On logic in tests
There are cases where we could include some logic in the source code in order to help us performing some functional tests or end-to-end tests
Unit testing is an area of software engineering where people seem to become very dogmatic. "Do it this way or it isn't unit testing" - this can get in the way of actually doing tests. People have argued it each way and will continue to argue about it for quite some time.
One of my favorite documents on testing is The Way of Testivus - its a good (and humorous) read.
The thing is to write the test that needs to be written. If this means putting logic in there, then there's logic in there.
The danger of the this is who tests the logic in the tests (Test-Driven Hypocrisy? Who tests the test?). The issue being if your test logic and your business logic are both broke, you may miss an actual failed test.
On code with test logic
Another aspect to this question is the "we stuck some code in the build that goes to QA (and presumably to production - because you don't switch out the build after giving it to QA...) to make their job easier.
There's a real danger here.
When you put test code into the build it is possible that it will get tickled in production. "But that will never happen" has happened far too often. The code allows you to set the time stamp, or get into a certain state that allows you to do set some data without going through some other process.
These are bad things. Don't do them.
One example could be that we have some test code around date/time logic so that if the testers make server and client time different, this code could help them to perform some tests.
Don't do that. And here I'm being rather dogmatic. There's a difference between having the unit test code which never gets bundled into a production build where its important to do the testing... and code that is going to production.
Having test code in there that lets you bypass the normal flow of the code that a user would need to do has several issues with it:
- The full process isn't being tested. The QA tester is jumping around the code in a way a normal user can't. This means that the actual workflow isn't being tested. You've stuck data in some place through an admin/test interface that initializes the structure before using it... but your normal code doesn't and you've got a bug that QA won't find.
- There's a hook in there that someone else can use. We know all the users are nice and don't go poking into places they shouldn't be looking. Sure you've got it hidden needing to hold down the shift-control-alt and 'cat' at the same time... but you've never had a cat actually step on your keyboard to do this in a way that only a cat can. And cats aren't the most nefarious of the keyboard users - people with less than honorable intentions will find this hook too.
If you need an environment that makes a particular thing easier to test, set up that environment. You want the testers to have the ability to do some test with the client and server out of sync? Create a VM that recreates this environment easily rather than inserting some code that makes the client interpret its timestamps as 30 seconds in the past (or future).
Don't put test code in the production build. Make sure you test the production build. This may necessitate having longer testing processes, but the alternatives can be very bad (missing a bug or letting someone use the software improperly).