Where communities thrive


  • Join over 1.5M+ people
  • Join over 100K+ communities
  • Free without limits
  • Create your own community
People
Activity
    Bruno Bonanno
    @bbonanno
    Thanks!
    Sadly I just realised the build is not running, so this is blocked pending an open issue :(
    Darren Bishop
    @DarrenBishop
    No probs. It’s there when the time comes. I’ve worked around it in my current tests
    Darren Bishop
    @DarrenBishop
    hi @bbonanno, when verifying i.e. with obj.method(longCaptor, stringCaptor) wasCalled n.times, do the macros internally discount that particular call to obj.method(…)?
    i am observing a weird behaviour where the longCaptor is reflecting an extra value than stringCaptor and it happens to be 0L i.e. the default for the primitive (what longCaptor.capture yields, presumably)
    any thoughts?
    Darren Bishop
    @DarrenBishop
    *sorry, ignore the diff number of values captured; they both are consistent in capturing 1 more value than expected
    it seems that stubbing with ... returns … ignores the invocation of the method/function being stubbed, where as … wasCalled … does NOT ignore the invocation of the method/function being verified, throwing it out by 1 and yielding the default (.capture) value as the first captured value
    i’m not well versed in macros, so i am struggling to investigate at all
    Bruno Bonanno
    @bbonanno
    hmm, I don't fully understand, would you mind rising an issue with a code snippet that can be used to reproduce?
    Darren Bishop
    @DarrenBishop
    i will try
    out of curiosity, is the default value for a Captor[Array[Byte]] the value ”test” (but in bytes)?
    Bruno Bonanno
    @bbonanno
    I don't think so
    it should be the empty array afaik
    Darren Bishop
    @DarrenBishop
    right. pebcak
    Darren Bishop
    @DarrenBishop
    sorry, again. just checked and my mocks were not reset. please execuse all the noise
    Bruno Bonanno
    @bbonanno
    np, shit happens
    Oliver Schrenk
    @oschrenk

    AsyncFlatSpec with MockitoSugar are not being found/executed:

    If I run this

    import org.mockito.scalatest.MockitoSugar
    import org.scalatest.flatspec.AsyncFlatSpec
    import org.scalatest.matchers.should.Matchers
    import scala.concurrent.Future
    
    class AcmeSpec extends AsyncFlatSpec with Matchers with MockitoSugar {
      "Simple" should "fail" in {
        Future.successful(1 shouldBe 2)
      }
    }

    I get

    [info] AcmeSpec:
    [info] Simple
    [info] Run completed in 131 milliseconds.
    [info] Total number of tests run: 0
    [info] Suites: completed 1, aborted 0
    [info] Tests: succeeded 0, failed 0, canceled 0, ignored 0, pending 0
    [info] No tests were executed.

    No test are executed. Just removing with MockitoSugar and not mixing in the trait but without any code change, the tests are found, executed (and fail).

    Scala 2.13.4
    "org.mockito"       %% "mockito-scala"            % "1.16.15",
    "org.mockito"       %% "mockito-scala-scalatest"  % "1.16.15",
    "org.scalatest"     %% "scalatest-flatspec"       % "3.2.3",
    "org.scalatest"     %% "scalatest-shouldmatchers" % "3.2.3"

    Why does mixing in MockitoSugar silently suppress running the tests? Any clues? Anything wrong in my test code?

    Bruno Bonanno
    @bbonanno
    @oschrenk you're probably looking for AsyncMockitoSugar
    Oliver Schrenk
    @oschrenk
    Ah! I am indeed. Is there a way of improving the output? Maybe an error message when mixing "incompatible traits"
    Bruno Bonanno
    @bbonanno
    Will have a look :)
    Darren Bishop
    @DarrenBishop
    @bbonanno sorry, i didn’t have github notifications configured correctly. have updated the PR as requested
    Michael Goytia
    @HurricaneGoytia_twitter
    Question, I am very new to scala, I see it is possible to mock one object with the advent of 1.6 but I am wondering if it is possible to mock multiple objects ?
    Michael Goytia
    @HurricaneGoytia_twitter
    that being in the same context of a function which used multiple objects
    Bruno Bonanno
    @bbonanno
    Yes it should work, just nest the mocking statements and you should be in business
    Michael Goytia
    @HurricaneGoytia_twitter
    will try and report ty
    Michael Goytia
    @HurricaneGoytia_twitter
    So I have read a lot of answers on stackoverflow that say mocking/spying are code smells. I just started “converting” to a scala dev from an extensive background in python (used mocks and patching extensively) and java (used Mockito there). I have found that good unit tests explore all the paths of your code and that we can isolate testing the functionality of just the a function by adding mocks/spys/patches/stubs. I have tried to apply such strategies as those found in http://engineering.monsanto.com/2015/07/28/avoiding-mocks/ but still come to a point where mocks are useful even when trying to stub as much as possible. I feel like it is very difficult to structure everything(especially leagacy code) into a functional manner when in the end we use mutable datastores such as a database. We can have patches of pure functional code but when it comes time to update, insert into a database or do anything that is not pure we have missed the mark of optimal functionalism. Now I would desrcribe a TDD process of constructing a functional paradigm until we get to the entry of impure functionality. For this I see an approach with unit testing all the functions and stubbing as much as we can and filling in with mocks and spys. I then would add intregation testing for all the impure functionality. I have found this approach to be a good current strategy for a play application we have. I am asking for thoughts on this as I try to get a greater understanding of developing in scala
    Bruno Bonanno
    @bbonanno
    I partially agree with that, my take is that in a functional program, most of the functions will be pure and hence mocking should be pretty much unnecessary, so there I totally agree that it could be a code smell
    now, any program to be useful needs to interact with the external world (UI, databases, IO, etc) so in there mocking works really well to me
    what I don't agree is the stubs bit
    I'll pretty much always prefer a mock over a stub, my reasoning being
    a) a piece of code I need to code, this means that if it is complex enough it may introduce its own bugs that could lead to false negatives/positives
    b) mockito-scala gives you so many tools out of the box to ensure your test is clean and it does what's supposed to do that I find that tests using mockito are pretty much always clearer, more succint, and more reliable than the ones that use stubs
    c) less code is better code, this links to a)
    d) do not re-invent the wheel, if you have a tool that allows you to impersonate dependencies, why on earth would you do it by hand
    Bruno Bonanno
    @bbonanno
    also, it's a bad practice to mock (or even stub) code you don't own
    so for your dependencies I'd create abstractions you control and integration-test them against the real thing, then the rest of your tests can use mocks of said abstractions (services, repositories, etc) you created
    Michael Goytia
    @HurricaneGoytia_twitter
    @bbonanno thanks for your response. Gives me a lot of valuable insight to think about
    Darren Bishop
    @DarrenBishop
    second @bbonanno; i do end-up building up a ‘small-lib’ of stubbing code - usually from refactoring and DRY’ing out a growing number of tests - but these are always (almost) producing containers or collections of value classes, behind functions with semantics that are obvious in the domain. the interesting thing here is, when that particular ‘smell’ gets too pungent, it’s probably a sign to break-out ScalaCheck, which is awesome
    but why i really came here today: does anyone know how to make individaul stubbed methods lenient within the IdiomaticMockito style of stubbing e.g. obj.func(*) answers ((x: Int) => x * 2 + 1) isLenient does not get me any mileage
    Darren Bishop
    @DarrenBishop
    obj.func(*) isLenient()
    obj.func(*) answers ((x: Int) => x * 2 + 1)
    seems to work
    Michael Goytia
    @HurricaneGoytia_twitter
    @DarrenBishop thanks for your insight as well. Need to checkout out ScalaCheck
    Bruno Bonanno
    @bbonanno
    @DarrenBishop what’s the thing that ‘isLenient’ doesn’t do for you?
    Darren Bishop
    @DarrenBishop
    I was re-stubbing a mock in a way you’d probably disapprove of, while batch processing a sequence of items; the last re-stubs never get called as the sequence was exhausted
    isLenient() works now; I was using it like a post-fix operator on my stub, which just seemed like the right way, but I believe I found the correct usage in the end (right?)
    Bruno Bonanno
    @bbonanno
    But if it used at least once, why do you have to make it lenient?
    Darren Bishop
    @DarrenBishop
    The api I am working with needs a factory of writer objects - you maybe cringing already - the mockedFactory returns one of small set of mockedWriters, selecting and re-stubbing a mockedWriter based on the factory method args. The last time the factory gets called, which is expected, the returned writer(s) don’t get used, where all the input items are finished
    I later verify the call counts are correct
    It sounds more complicated than it is
    Bruno Bonanno
    @bbonanno
    All right 😅
    Darren Bishop
    @DarrenBishop
    😅