Live data from Hacker News

Database mocks are not worth it

shayon.dev

151–160 of 268 posts

Re: Database mocks are not worth it

#151
post #31

Earlier quoted context omitted.

Don't know what language or database you use, but check this out: https://github.com/peterldowns/pgtestdb If you happen to use Postgres, the approach is ultimately portable: it uses Pg database templates (also, regarding perf, the author recommends using a ramdisk and turning off fsync on your test DBs; you'll see this in the project readme). But you’ll have to write the code yourself.

Author here, thanks for linking my project — I hope it's been working well for you!

This is so great Peter-- first I've heard of pgtestdb and it's immediately useful for me. How can people donate money to the pgtestdb project? Or hire you for consulting for pgtestdb? I'm joel@joelparkerhenderson.com and would love to help fund your work.

Re: Database mocks are not worth it

#152
No... for pete sake no!

The whole point of mocks for data base is not to test schema changes, it's to test a unit of code. These most certainly do not change the additional requirement of integration testing with real database tables. That usually happens after all the unit tests, obviously, because why spin up a big heavy database test pipeline if the code logic fails.

Re: Database mocks are not worth it

#153
post #151

Earlier quoted context omitted.

Author here, thanks for linking my project — I hope it's been working well for you!

This is so great Peter-- first I've heard of pgtestdb and it's immediately useful for me. How can people donate money to the pgtestdb project? Or hire you for consulting for pgtestdb? I'm joel@joelparkerhenderson.com and would love to help fund your work.

I sincerely appreciate the sentiment and the offer — but pgtestdb is MIT license, actual, for real, not kidding, open source. No payment necessary; please enjoy.

(I'm always open to discuss potential contracts or consulting opportunities. If you have one that you think might be a good fit, my email is in my profile here and on github and on my homepage.)

Re: Database mocks are not worth it

#154
post #2

For tests, first use a real database. If you can't because the database just doesn't want to (ahem mongo ahem) then use a fake. If you can't use a fake, stop lying and use a fake. Mocks for databases are extremely brittle and complicated.

> If you can't because the database just doesn't want to (ahem mongo ahem)

Could you elaborate what is the problem with mongo here? You can run it with testcontainers like any other database.

Re: Database mocks are not worth it

#155
post #129

Earlier quoted context omitted.

Mocks are great for testing specific code paths, but if you need to do that, there is usually a better way of doing it. Mocks hide contractual incongruities. For example, a function that returns either "fizz" or "buzz" that gets mocked out. If it gets changed to also return "bar", and you forget to update the mock, you've got a time-bomb in your code.

The person who changes it should write a test to verify his change, right? Ultimately the person should write the test in the same file as the previous tests, chances are high it will be seen there. And even if not, the person doing the change should write a test, so no time bomb there? And yes, people forget to write tests, sure, but even then it would be a time bomb without mocks. I‘m not a friend of mocks either,…

Generally, mocks are quite far away from what they are mocking. You might mock out a library, for example. I can guarantee you that the library author will not show up at your workplace to update your mocks.

Re: Database mocks are not worth it

#156
In addition to what I've read here in the comments (that mocks are inaccurate, etc) I'll say that mocks also tend to just be plain overly verbose, at least in my stack. We do a lot of our heaviest testing on our usecase logic, which is almost all very imperative and calling the DB + 3rd party APIs in various ways.

Mocked tests here tend to be many times as long as the actual implementation, grow with the size of the implementation, and also tend to break immediately if you change the internals of your code (because now new things are being called, or not being called). Having hundreds of such tests can make refactors and serving new requirements a lot more annoying.

The little "trick" of using SQLite to speed up integration tests has also bit me multiple times. Turns out the various RDBMSes are not in fact, all the same, and the details start to matter a lot very quickly.

Re: Database mocks are not worth it

#157

Don’t code with mocks period. Structure your code such that it has a functional core and imperative shell. All logic is unit testable (functional core). All IO and mutation Is not unit testable (imperative shell). Mocks come from a place where logic is heavily intertwined with IO. It means your code is so coupled that you can’t test logic without touching IO. IO should be a dumb layer as much as possible. It should b…

how do you test the imperative shell except with mocks? Suppose you're calling an external API

The jargon around all this stuff is terrible. What I would probably write is, like, a fake version of that API, one which runs out of process from the library or test, and which can be "programmed" from the test set up -- "expect these requests, serve these responses", etc.

Is that a mock? I don't know. It sure does resemble one, but it doesn't use dependency injection or other runtime tricks which I'd associate with classic "mocks"; it's just another program you write to support the tests. The imperative shell doing I/O needs to be configurable to support this (think a "widgets API base URL"), but that's it.

Re: Database mocks are not worth it

#158

Don’t code with mocks period. Structure your code such that it has a functional core and imperative shell. All logic is unit testable (functional core). All IO and mutation Is not unit testable (imperative shell). Mocks come from a place where logic is heavily intertwined with IO. It means your code is so coupled that you can’t test logic without touching IO. IO should be a dumb layer as much as possible. It should b…

how do you test the imperative shell except with mocks? Suppose you're calling an external API

How do you test that the external API returns are correct?

Re: Database mocks are not worth it

#159

Don’t code with mocks period. Structure your code such that it has a functional core and imperative shell. All logic is unit testable (functional core). All IO and mutation Is not unit testable (imperative shell). Mocks come from a place where logic is heavily intertwined with IO. It means your code is so coupled that you can’t test logic without touching IO. IO should be a dumb layer as much as possible. It should b…

Any suggestions on where to read about this more?

Re: Database mocks are not worth it

#160
post #146

Earlier quoted context omitted.

You failed to read and/or understand what I wrote. Also how do I fail a test for a new code addition I didn’t even write? Unit tests dont test impure functions all they do is test pure functions. Impure functions aren’t unit tested period. So when someone writes an impure function I don’t like what happens? Nothing. It wasn’t part of unit tests annyway, understand? If you’re referring to integration tests well a newl…

How do you write the expected return from an external API in your test setup?

That’s an integration test. Your external api returns a number, let’s say 10. You have two local functions. One that is very general and fetches that number, and another that transforms that number. Your local transformation function is the one that is tested. The other function is part of integration tests and in general can’t be unit tested.
Post reply on HN