
Simulating any system date for TDD by library interposing - kunley
http://irekjozwiak.com/entry/2010/01/10/Testing-Date-Related-Code-With-Library-Interposing.html
======
kwantam
Intercepting system calls via LD_PRELOAD is a hugely useful approach for many
situations. Got a binary-only piece of code that's creating ghost temp files
you want to poke at? Intercept unlink(). Need to quickly (and dirtily) hack an
executable that isn't designed for concurrency into sharing a file with other
instances of itself? Intercept open().

On the flipside, when trying to do things as securely as possible, never
blindly trust dynamic linkage into library functions: attackers can and will
use such techniques against you. Reflections on Trusting Trust[1] becomes
scarier when you start thinking about all the venues you open with dynamic
library linkage.

[1] <http://cm.bell-labs.com/who/ken/trust.html>

~~~
kunley
This insecurity of dynamic linkage is a very interesting topic and I never
considered it seriously before. Thanks for pointing it!

------
stcredzero
I wish we had something like this on my last project. On my last project,
there were two separate systems for determining the local Timestamp. One of
them was based on the time from the local machine's clock. The other took time
from a central mainframe/transaction processing system. (Call these system-A
and system-B) We really could've used something like the article proposes for
_both_ systems.

Here's the thing: The application would calculate the timezone based on
system-A, then use the time from system-B to do a lookup into a GMT-based
table using system-B's time. All well and good, until the testers tried to
test calling outside allowed hours by changing their local system clocks. This
mess resulted in trying to look up entries in the table for timezones the
middle of the Pacific. Boom!

The worst part? Trying to explain to the testers how this was an inherent flaw
in the legacy system and not a result of the upgrade. (Yes, I would've changed
it if I were allowed to.)

------
jamie_ca
I've done this many times in both unit specs and Cucumber (what it looks like
he's targetting), and I manage to get away with defining the Given step as
stubbing Time.now. No need to get hairy with C at the low level.

~~~
regularfry
He's not targeting cucumber, he's targeting GHC. It's much easier in Ruby than
in Haskell.

------
jerf
That feels even _more_ wrong for Haskell. I think that the Haskell way really
is that you have pass the function in. Probably the worst thing about Haskell
is that it _aggressively_ has no concept of a global environment.

That said this may well be the most practical approach; "the Haskell way" and
"practical" are not always exactly buddy-buddy. I'm just responding to the
question of "the Haskell way".

~~~
kwantam
I can see your point here, but since time is fundamentally an external datum
provided by the system, in my view there's no reason to screw with Haskell's
internals when you can just produce the necessary simulated environment in
which your runtime lives. Moreover, by doing it this way you can use exactly
the same code in testing as in production, reducing the risk of something
going wrong when you change from the former to the latter codebase.

~~~
kunley
I totally agree. The OP came with a great way of simulating certain states of
the external environment for the purpose of tests and completely independently
of the implementation. This decoupling seems uber cool.

