Live data from Hacker News

Don't Use Mocks

joeblu.com

71–80 of 85 posts

Re: Don't Use Mocks

#71
post #5

Nah I'm about done working on rails codebases with 2+ hour CI cycles because developers insist on hammering a database in unit tests.

2+ hour CI means something else is going wrong. at shopify, our CI is like ~10 minutes and we typically avoid mocks.

Re: Don't Use Mocks

#72
post #19

Can we not have articles like this with blanket statements like this please? As with everything in software, no one size fits all. Mocks have their place. There are situations when the only way we can test something out is to mock out a certain function call. Sometimes our dependencies are so complex and deep that we cannot just replace it with a fake. But with a little mock we can replace a function or a class withi…

Actually, I feel that making strong statements of opinion regarding code style is probably the best way to go about doing things.

Re: Don't Use Mocks

#73
I mostly agree, but with one exception - I think mocks are still useful for RPCs to other systems, where you want to test that you:

1) Call the right method on the interface with the right data, and

2) Correctly handle different return values from the RPC.

If you change your code to call a different RPC method your test _should_ fail, I'd argue that's exactly the point of this sort of test.

On the other hand, for testing code that you entirely control, I 100% agree that a fake would provide a better test,

Re: Don't Use Mocks

#74

Earlier quoted context omitted.

Maybe more eloquently put: https://martinfowler.com/articles/mocksArentStubs.html

Mocks, fakes, stubs. Every time I read this article I end up more confused than I was before.

I like Uncle Bob’s explanation:

https://blog.cleancoder.com/uncle-bob/2014/05/14/TheLittleMo...

Re: Don't Use Mocks

#75
post #5

Nah I'm about done working on rails codebases with 2+ hour CI cycles because developers insist on hammering a database in unit tests.

2+ hour CI means something else is going wrong. at shopify, our CI is like ~10 minutes and we typically avoid mocks.

That may be the wall clock time but how parallelized is that?

Re: Don't Use Mocks

#76
post #34

The point is: if your tests just assert which methods are called on dependencies with what arguments (or something close to that), they are extremely coupled and brittle. Almost any change in the implementation will require changing such tests. And by their nature, they probably test some minor low-level things, that are not all that valuable to assert anyway. Mocks enable and encourage this kind of testing. Better t…

> The point is: if your tests just assert which methods are called on dependencies with what arguments (or something close to that), they are extremely coupled and brittle. I'll go further. These tests are worse than useless; they're harmful. - They're the very definition of testing an implementation - You will wasted a ton of time updating them when your implementation changes - They give a false sense of security/p…

Sometimes they're still necessary. E.g. many devices need particular sequencing in their power-up between multiple rails. The Intel 82598 Ethernet Controller datasheet[1] page 129-132 shows this nicely. If you're writing a driver you have to test that the appropriate GPIO control calls happen in the right sequence (and with the right timings). Of course it's an implementation detail, different ethernet controllers have different power-up sequence requirements, and thus different drivers.

Of course you don't want to have to use real hardware for these tests, especially because with some devices incorrect power-up sequencing can cause permanent damage. So you write mocks for the various hardware functions and test the driver with those, and use their counters & the test harness's logging to assert that the sequencing and timing is correct.

[1] https://www.intel.com/content/dam/www/public/us/en/documents...

Re: Don't Use Mocks

#77
post #74

Earlier quoted context omitted.

Mocks, fakes, stubs. Every time I read this article I end up more confused than I was before.

I like Uncle Bob’s explanation: https://blog.cleancoder.com/uncle-bob/2014/05/14/TheLittleMo...

That is a solid way to introduce the different test doubles. Thanks for the link. I agree, stubs and spies are my daily bread. I also use fakes very regularly. I hardly ever use mocks, for the same reasons in the post.

Re: Don't Use Mocks

#78
post #64

My goto simple example here for dumb mocks is a multiply function. You are doing it wrong if you have: MyMock.Mocks(myMultiplyFunc).WithArgs(3, 4).ToCall(myAddFunc).Times(3).WithArg(4).ExpectsResponse(12). Your multiply func being backed by add is not important to the unit test for multiplying. If you change it to have special handling for bitshifting in different cases, your mock tests break. Badly. Mocks add coupli…

> Make a dependency interface "SendEmail(userID int, content []byte) (SendGridResp, error)". Inject that. Am I an idiot for thinking of this as a Mock? This is how I mock things anyway

Mock vs a fake. The difference lies in where the behavior is specified. In a fake, the behavior is hardcoded or simple. With a mock, it is each test that says what the behavior is.

The two scale differently. Mocks are per test, fakes are once.

Re: Don't Use Mocks

#79

Earlier quoted context omitted.

I once worked with a mockist who mocked out hashtable. It didn't end well when we had to debug his code. I once knew a mockist who mocked out all the external code's behavior, but didn't add tests to ensure that the external code behaved as they expected. That didn't end well either. Just don't use mocks, unless they're the simplest thing that could work (usually not).

what does it mean “mocked out hashtable”? Whole hashtable? Or what? You mock interface/api of “something” you depend on to model the behavior you might deal with within the part of code you test. thats it. nothing else. during unit test phase I want to make sure that this exact code works as a state machine given all the possible inputs/outputs and that it handles any possible situation any dependency can cause. If y…

I find that mock-heavy tests I've interacted with are low ROI: they don't find or predict bugs, require significant work to write, and often have to be updated when the code under test has changed even when the actual feature/case being tested has not changed.

While mocks can be useful, IMO "never use mocks" isn't a terrible rule of thumb.

Re: Don't Use Mocks

#80
post #64

Earlier quoted context omitted.

> Make a dependency interface "SendEmail(userID int, content []byte) (SendGridResp, error)". Inject that. Am I an idiot for thinking of this as a Mock? This is how I mock things anyway

It is maybe a semantics issue. See https://martinfowler.com/articles/mocksArentStubs.html . Traditionally, a mock asserts against internal behavior while a fake does not.

I think it probably is, it seems like certain parts of the tech community has a more specific language for talking about things, and other parts have a less specific.
Post reply on HN