What's a healthy code:test ratio?

Hey,

I’m just wondering what people consider to be a healthy code:test ratio
(as
shown in rake stats).

Our new code base is currently 1:2, obviously not that great, what
ratios do
you lot have?

I’m thinking 1:4 would be a nice ratio, though that’s not a founded
statement.

I realize this isn’t an accurate metric for analyzing test coverage, but
it’s interesting at least.

Cheers
Ian

I think you almost answered your own question. What matters is code
coverage, and completeness of cases, not bulk ratios.

At the same time I can not imagine a project having every case tested
completely. That would take more like 1:10 or more. So testing what
is immportant, and adding tests for every reported defect is at least
a minimum.

Michael

Ian L. wrote:

I realize this isn’t an accurate metric for analyzing test coverage, but
it’s interesting at least.

1 line of code for every 2 lines of test is head-and-shoulders above the
majority of software projects, including your competition’s.

Let’s assume you are using Test-Driven Development, where you make tests
fail before writing code to pass them. (Otherwise even achieving 1:1
would
be really hard!)

Pay attention to your test quality. If you frequently clone-and-modify
test
cases, and if the test cases get rather long and do many things, your
code
will indeed resist bugs, and you shouldn’t spend much time debugging.

However, your tests won’t be very DRY. This could account for a high
test
line count. Tests should be readable, individual, and self-documenting.
If
they do too many things, and if they have too many lines, there are some
useful techniques you can use to merge them and make them more useful.

You could, for example, perform the “Extract Method Refactor” (look it
up)
to merge common assertion code into an application-specific assertion.
If
your application requires tied shoelaces, you could write
‘assert_laces_tied(shoe)’, for example. This improves the test’s
readability.

Next, many tests follow the “Execute Around Pattern”. Look that up too -
Ruby does it all the time. If your test creates a resource, then calls a
tested method, then verifies that resource, you could encapsulate the
“before” and “after” concepts, and put the actual test into a block. For
example:

def test_shoe_laces_tied
assert_laces_tied do |shoe|
shoe.go_jogging(5.minutes)
end
end

Now you can write many test cases that create shoes, call different
methods
on them, and assert that their laces remain tied.

The next more advanced form of this concept is the “Abstract Test”. That
means you write two test suites as modules (not classes), and then you
write
some Test::Unit::TestCase classes that include these modules, and apply
different setup() methods to them. Each setup() method creates a
different
object, and the inherited test cases check that they all behave the
same.
Abstract Test is a good way to enforce objects that obey the Liskov
Substitution Principle.


Phlip
Test Driven Ajax (on Rails) [Book]
“Test Driven Ajax (on Rails)”
assert_xpath, assert_javascript, & assert_ajax