What you call integration testing, I call sloppy programming

Re: Your insistence on distinguishing unit testing and integration testing.

You make the distinction between unit testing and integration because you are a sloppy programmer. You throw side-effects around like a 5 year old in a play pen. You do not care for intellectual discipline in your thinking process. Nor do you care for high-level abstraction or composition of your software. Instead, you insist on this dogmatic “test driven” nonsense. You do this because you are married to the FORTRAN family of programming languages. Your so-called integration tests exist because you have implicit free variables in your equations like a ‘good little imperative programmer’. If you did decide to apply discipline and consider your side-effects, you’d see no distinction between unit testing and integration testing. I realise that this possibility escapes your feeble and narrowed mind at this stage of the socratic midwife process.

When you do unit test, you’re using an awfully impoverished method. I mean, “assert this and assert that”. Give me a break! You think this is going to “drive” something? Anything? OK, it drives me bonkers to think that you insist on spreading mythological, pseudo-scientific, fanatical bullshit (excuse the term, but it is most accurate) and have followers repeat said myths in such an obedient I-cant-think-for-myself fashion. You think you’re contributing to the “design” and “quality” of your software? How mistaken you are and what empathy I feel for you.

I implore you to retract your silliness and take seriously the charge that you are a sloppy programmer (evidence forthcoming). Your dependence on “agile this” (I play A grade squash, I’m perfectly agile, thanks) and “test drive that” are entirely dependent on an existing sloppy form of programming. Furthermore, these workarounds not only rest on a flawed premise, but they are extremely diluted anyway. Even with the given silly premise you can significantly improve! But I won’t tell you how, no not yet. First you must prepare for an act of apostasy, which I understand can be very traumatic. So I can’t help you until then, but in the meantime, I kindly ask that you stop imposing your silly ideas on me, because yes, they are silly.

See you on the other side.

17 Responses to “What you call integration testing, I call sloppy programming”

  1. trav Says:

    OUCH BURN!

  2. Bolly Says:

    OK, I’ll take the bait.

    I’m not sure what experience you come from here, but I find your conclusion remarkably glib, and over-anxious to place all responsibility for everything at the door of the poor programmer.

    I’m going to leave aside a number of your wild assumptions, and try to focus on the substantive issue. Integration testing is absolutely required in the real world.

    In that real world, there are many legacy systems which are poorly documented and understood. The company which depends on them never invested in developing a rich suite of documentation for them. Back in the day, when this middle-aged company was a sprightly new kid on the block, getting new functionality delivered was the thing, not delivering the associated documentation to ensure future maintainability; not even designing an architecture to ensure that the system could be easily extended. Within a year, the software was being changed to deliver new functionality unimagined by the visionary who originally specified it. He just had to adapt as the requirements became clear as people started using it. Everyone involved in getting the system off the ground has now longs since left the organisation, and those who have inherited this complicated, poorly architected, built-by-bolt-on system are afraid to touch it. They have requested the funds to rearchitect it, but since no-one really understands what it does, but it still seems to do it ok, no-one dares touch it.

    Also in that real world, there are an absence of product managers in some of those companies. There are lots of people chamioning new initiatives and kicking off new projects which require changes to many different systems. At any time, a given system might be under development to meet the requirements of 10 different projects, none of which gives a rats ass about the other 9, and each project has its own (half-baked) requirements and its own (manually operated by contract staff who don’t know the product from adam) test plan. It falls to the developers to try to ensure that the version which they are building meets the requriements of all the individual projects, but with each project beign tested in isolation and only testing what it cares about, there is a big risk of unintended consequence.

    Many of these projects will require changes to vendor systems. As a vendor, you get to have someone specify exactly what the interfaces and expected behaviours are. The vendor may even get to demand that stubs are provided for any interfaces. The inhouse developr needs to provide the stubs, psossibly, long before the internal customer has actually committed to the requirements - as if they ever do. This insulates the risk to the vendor. As late changes are unearthed in the project, or as any unforeseen conflicts between concurrent projects are discovered, the cost of changing what the vendor has to deliver will be seen as prohibitive, so the inhouse developers will be asked to come up with a workaround.

    Requirements will inevitably change throughout the life of the project. Multiple versions of any given product will be in development in parallel, for varying deployment dates. The sequencing of the deployments will frequently shift as the business reacts to changes in the market. Version 14 is repropritised to come in ahead of Version 11, thereby changing the baseline for multiple versions of the code, and possibly requiring requirement changes or workarounds.

    With waterfall methodologies still in place in these companies, the business owner is under pressure to sign off on requirements by a given date. To do this, they keep the requirements as vague as possible, and neglect to advise some impacted parties of the changes until after the requiements deadline. This allows the project through the gates, and keeps the door open for them to completely change what it is they have asked for.

    So, in a world of undocumented legacy systems, litigous vendors, absent product management, tunnel-visioned project management, shifting priorities, workarounds, reliance on contractor development and test, late and vague requirements; as well as no investment in documentation, pressure to cut corners, high staff attrition and many other complications introduced by management foulups - there are many, many reasons why integration testing is absolutely required. And the vast majority of them have little, if anything, to do with sloppy programming.

  3. Matthew Says:

    There are a lot of smart people out there in the industry, with maths or comp sci degrees who are well aware of functional programming techniques, follow things like Haskell and QuickCheck in their spare time, and push for languages which go a signficant step of the way (like Ruby and Scala) in their day jobs.

    There are also significant practical reasons why we’re not yet using these techniques to do large scale software engineering. Patronising us won’t help. Addressing some of our issues will help.

    - Complex legacy platforms (Such as ‘The Web’ - HTTP + XHTML + CSS + 3 or 4 different subtly incompatible Javascript, DOM and rendering engine implementations + Flash + more), with multiple layers, languages, runtimes, all with patchy, inadequate tool support for functional programming; many attempts to mask with higher-level abstractions prove unnacceptably leaky (in the sense of ‘leaky abstractions’), inefficient, unscalable, or some combination thereof

    - General friction to change in the industry - legacy code in imperative languages, Retraining and recruitment costs for functional programmers etc

    - Lack of battle-tested methodologies, techniques and examples for doing software engineering “in the large” with a truly-functional-language-based stack, outside of a few conveniently-especially-suited domains (often requiring conveniently-self-contained and easily-specified systems)

    - Lots of trivial examples proving correctness of fibonacci functions, and other simple algorithmic tasks, few for testing interactions between complex distributed systems (see the above poster)

    I’m afraid I don’t really follow the MS ecosystem though, so maybe F# is starting to solve some of these. If so, I would be glad to hear about it. Not glad to be patronised though. But you knew that.

  4. Tony Morris Says:

    Hi Matthew,
    A couple of points on which we disagree:

    1) Pushing for Ruby will not improve software development. I certainly do not advocate it. I have reasons, but I find the discussion extremely uninteresting, so please excuse my lack of will to elaborate with what is likely to infringe on many people’s belief system.

    2) I am not patronising anyone. I am putting forward an open proposition for analysis. That it infringes on your definition of self-worth is of no importance to me, even if I wanted it to be. I do not write to appease others.

    3) What I did know was that I’d attract comments containing silly accusations further contributing to my feeling of empathy for others.

    Please be glad, regardless of what others say.

  5. gerel Says:

    .
    The only solution is to eliminate OOP from the map, which is hardly going to happen ’cause it’s supported by the entire damn industry
    .

  6. Shanon Says:

    mildly entertaining with absolutely no practical substance…

    if only we were all perfect.

  7. bob Says:

    Sounds like a healthy case of circle-jerking to me. Where’s this so-called evidence?

  8. Jason Says:

    In response to the response to Matthew:

    1:) There was an apparent lack of will to elaborate in the original posting. Not surprised you’re not willing to elaborate in the follow-up.

    2:) You are not putting forward an open proposition for analysis. Analyzing something requires data. You didn’t provide any data. You provided a bunch of unsubstantiated opinion without a lick of data behind the opinion. You may not write to appease others but was the point of the original post to actually accomplish something? What the post does come across as is a lazy programmer coming up with a cheap excuse to avoid testing. The fact that you think testing is a waste of time doesn’t make it so.

    3:) No idea what your point is here since two of the three comments above yours actually had more substance than your post did.

  9. Ricky Clarkson Says:

    So what I think Tony is trying to say is: Prove (possibly by exhaustive testing) that your code follows the contracts it sets for itself, and you won’t need to test the interactions between parts of code.

    Taken literally, it seems true, but exhaustive testing seems impossible for many cases, and proof is mathematically beyond most programmers, so *some* integration testing is needed. Presumably the more you can prove the less integration testing you need.

  10. Tim Garrett Says:

    Unit testing = your code.

    Integration testing = other people’s code.

    As much as I like good clean code, I have had to make sacrifices in idealism to make things work with other people’s crappy code. Things that can only be found out by integration testing…

  11. Jesper Nordenberg Says:

    Hehe, you’re a funny guy Tony.

  12. Tony Morris Says:

    Hello Jesper ;)

  13. soylent.green Says:

    plonk, go have your fish >

  14. Berlin Brown Says:

    Thanks for telling it like it is Tony.

    I have always been hammering the unit-testing/agile nazis. Even from just observational standpoint, you can start to see holes in the unit-testing agenda.

    So you are telling me, if I have full code coverage with statements like the following:

    assert “dog” row.get(1)
    ….
    my code will be bug-free?

    It never stuck for me. The java/junit oriented unit testing is yet another set of practices that survived only based on blogosphere propaganda. Obviously, you have to test code and test the application to ensure that the requirements are met it is just a matter of how you go about doing it. The Junit nazis say you shouldn’t write any code unless you write a junit test-case first, that is absurd. Especially in the Java world. Java developers are known for following bad practices and being lazy (good example, Sun engineers); why do we expect the Java community to suddenly follow best practices, write quality code AND write continuously write quality unit-tests. It is never going to happen.

    To Jason: Tony probably didn’t provide any statistics because there probably aren’t any valid statistics out there. Rails is full of unit-test nazis and probably has full test coverage. What does that mean? Is Rails bug-free?

    Martin Fowler and his band of merry-men at ThoughtWorks probably are just using this scheme to collect on more consulting fees. “Well, if we add full coverage, that will be an extra $100,000; if you don’t do it, your code will suck. Write the check”.

  15. Berlin Brown Says:

    sorry for the typos.

  16. Stefan Wagner Says:

    I like ((((unit-testing)-testing)-testing)-testing)-testing.

    And yes - of course I write them first. ;)

  17. Stefan Wagner Says:

    Funny layout-algo in use.:)
    I should have looked at the preview.
    It’s like unit-testing.

    I like ((((unit-testing) -testing) -testing) -testing) -testing.

    And yes - of course I write them first (but then I don’t start them.) :)

Leave a Reply