Catching typos in scripting languages

Question:

If your scripting language of choice doesn’t have something like Perl’s strict mode, how are you catching typos? Are you unit testing everything? Every constructor, every method? Is this the only way to go about it?

Asked By: Geo

||

Answers:

There are errors other than “typos”. If you don’t test something, knowing that something’s found misspelled variable names won’t assure you of much anyway.

Answered By: Pointy

Some editors (for example, NetBeans) analyse your code and underline “suspicious” parts, for example unused variables, which may be sign of a typo. NB also highlights the identifier above the cursor elsewhere on the screen, which also helps.

Of course, no clever IDE trick can replace proper testing.

Answered By: Mladen Jablanović

TDD — write your tests first, then the simplest code to pass the test. That way you can be more sure that you don’t have any untested code. This will help make sure you have fewer typos or other errors in your code.

Pair programming/code reviews — two pairs of eyes are better than one pair.

IDE with intellisense — not a panacea, but a great help in not making typos. If you use intellisense, you typically get substitution errors, not typos. These shouldn’t be hard to find with tests.

Answered By: tvanfosson

Really-thorough unit tests are the most important technique (yes, I do always aim for 100% coverage), as they also catch many other typos (e.g. where I write + and meant -), off-by-one issues, etc. Integration and load tests exercising every feature are the second line of defense against all kinds of errors (mostly, though, deeper and harder ones;-).

Next are tools such as pylint and pychecker and colorizing editors (I don’t use real IDEs, but they would also help similarly to how my trusty gvim editor does;-).

Techniques such as mandatory code reviews (e.g., cfr a video of an interview of mine on the subject here), while crucial, should focus on other issues — issues that automated tools just won’t catch, such as completeness and correctness of comments/docstrings, choice of good/speedy algorithms, and the like (see here for a summary of the talk I gave on the subject at the same conference as I got that interview at, and a link to the slides’ PDF).

Answered By: Alex Martelli

Many unit test tools can show the percentage of lines they tested. The closer this percentage is to 100% the less likely variable name typo was done.

Answered By: Boris Gorelik

I write all my Python code in eclipse IDE. As Mladen Jablanović has suggested, eclipse underlines suspicious parts.

Next step is to run the code. Now there are two kinds of errors that I am likely to face.

  1. Errors that the interpreter catches and gives me a line number for: These are typically quite easy to debug, especially if you print all the variables in that line just before that line, to make sure that they contain the values that you’d expect.

  2. Unexpected behavior: your code is fine and the interpreter doesn’t complain, but your code doesn’t behave the way you want it to. When this happens (rarely, because I usually design my modules quite well – a process that takes about 7 minutes – before I start coding) I start looking at modules/functions in the order in which they are called and try to execute the program in my head as the interpreter would see it. If that doesn’t work, then I go on to explore the debugger. Usually, it doesn’t come down to this, but if it does, it’s a pretty big bug and it would take quite some time to fix. Unit tests help, but frankly, I think that as a computer scientist, I should be able to debug it from an algorithms analysis perspective, which is generally faster than unit testing (at least for me). Plus, choosing to do an algorithms analysis over unit testing exercises my brain so that I don’t make such mistakes in the future, as opposed to unit testing which helps me fix the problem now, but doesn’t do much in terms of helping me avoid making the same/similar mistake in the future.

Hope this helps

Answered By: inspectorG4dget

In ruby, a misspelled local variable would cause the program to die horribly, which is fine.

A misspelled instance variable doesn’t cause the program to die horribly, which is bad. To detect such cases, use warnings. Unfortunately, you can’t easily tell ruby to treat warnings as errors.

Answered By: Andrew Grimm

In my case, I use unit testing extensively (developing in Python). Because there are many lightweight testing frameworks well integrated into the language (or IDE if you prefer), using them cause you almost no pain 😉

Look at this example:

def unpack_args(func):
    def deco_func(*args):
        if isinstance(args, tuple):
            args = args[0]

        return func(*args)

    return deco_func


def func1(*args):
    """
    >>> func1(1,2,3)
    (1, 2, 3)
    >>> func1(*func2(1,2,3))
    (1, 2, 3)
    >>> func1(func2(1,2,3))
    ((1, 2, 3),)
    """
    return args

def func2(*args):
    """
    >>> func2(1,2,3)
    (1, 2, 3)
    """
    return args

@unpack_args
def func3(*args):
    return args


def test():
    """
    >>> func3(func2(1,2,3))
    (1, 2, 3)
    """
    import doctest
    doctest.testmod(verbose=True)


test()

    -----------------------------
    Results: 

Trying:
    func1(1,2,3)
Expecting:
    (1, 2, 3)
ok
Trying:
    func1(*func2(1,2,3))
Expecting:
    (1, 2, 3)
ok
Trying:
    func1(func2(1,2,3))
Expecting:
    ((1, 2, 3),)
ok
Trying:
    func2(1,2,3)
Expecting:
    (1, 2, 3)
ok
Trying:
    func3(func2(1,2,3))
Expecting:
    (1, 2, 3)
ok
3 items had no tests:
    __main__
    __main__.func3
    __main__.unpack_args
3 items passed all tests:
   3 tests in __main__.func1
   1 tests in __main__.func2
   1 tests in __main__.test
5 tests in 6 items.
5 passed and 0 failed.
Test passed.
Answered By: PabloG

I presume by ‘typo’ you mean mistyping variable/function/class names. This is less of an issue in Python than in Perl, since Perl (and I believe Ruby) by default will automatically create a variable and initialise it to zero or “” on its first use. Python does not do this since it is an error to use a variable that has not been explicitly created, so in that sense it is already in ‘strict’ mode.

I use Vim with the pyflakes plugin, which underlines most kinds of typos as soon as you type them. I also use pylint and pychecker frequently since they can catch many other kinds of errors.

Another thing I do is make heavy use of Vim’s auto completion – I only type a name in full once, then on subsequent uses of the name type the first few letters and use <ctrl-n> or <ctrl-p> to cycle through the matches.

I also use Test Driven Development with the aim of 100% unit test coverage.

I find that the combination of all these practices means that problems caused by typos are virtually non-existent.

Answered By: Dave Kirby

In Groovy, the abstract syntax tree (AST) that makes up a program is readily available. So tools can be written that inspect the AST and issue warnings for things that are probably errors.

For example, GroovyLint will warn you if you try to call a method that doesn’t exist at compile-time, but is very close to one that does exist.

Example:

class Test{
    static def foobar(){ return 5; }
}

Test.fooBar() //Here GroovyLint suggests calling foobar instead of fooBar.
Answered By: Kyle