• Post Reply Bookmark Topic Watch Topic
  • New Topic
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Jeanne Boyarsky
  • Ron McLeod
  • Paul Clapham
  • Liutauras Vilda
Sheriffs:
  • paul wheaton
  • Rob Spoor
  • Devaka Cooray
Saloon Keepers:
  • Stephan van Hulst
  • Tim Holloway
  • Carey Brown
  • Frits Walraven
  • Tim Moores
Bartenders:
  • Mikalai Zaikin

What are some of the usual causes of tests which return null?

 
Bartender
Posts: 1868
81
Android IntelliJ IDE MySQL Database Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I'm working on a Spring Boot 2 project which is programmed using Kotlin and WebFlux/Projectreactor.io
Currently I'm trying to figure out why when I call a mocked method I get NPE, but when I call the method normally things work.

What are some common causes of a test null, but when you call the method outside of the test environment the code works?
 
Sheriff
Posts: 5555
326
IntelliJ IDE Python Java Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Usually with mock frameworks you get a null back from a method call on a mocked object, unless you've configured it otherwise. Perhaps you're calling a method on a mock object, they trying to do something with the object returned?
 
Pete Letkeman
Bartender
Posts: 1868
81
Android IntelliJ IDE MySQL Database Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I don't think I'm doing that, but I could be wrong.
Here is a link to the GitHub https://github.com/letkemanpete78/exercise-listing, but the code in question is listed below:
Unit test:Here is the code that the unit test is trying to execute and return a NPE
ExerciseService:
 
Rancher
Posts: 4801
50
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
OK, I don't know Kotlin, but hopefully I can interpret that code well enough.

Your mocking for save(ex1) uses an Exercise object that looks like it has an id of "1"?

The actual call to save appears to be using an Exercise object with a random UUID (called exerciseID).
I can't see how it can match, unless equals ignores the id.
This assumes that Exercise has some form of equals method in the first place.

ETA:  Indeed, the filename is essentially random (as far as the test is concerned) as well, as it uses the current time, whereas your ex1 in the test has "fileName 1.png".
 
Pete Letkeman
Bartender
Posts: 1868
81
Android IntelliJ IDE MySQL Database Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Dave Tolls wrote:Your mocking for save(ex1) uses an Exercise object that looks like it has an id of "1"?

Correct

Dave Tolls wrote:The actual call to save appears to be using an Exercise object with a random UUID (called exerciseID).
I can't see how it can match, unless equals ignores the id.
This assumes that Exercise has some form of equals method in the first place.


However shouldn't this return with an object that has an id value of 1 along with the other constant values?

Exercise, is a Kotlin data class which does indeed have an equals method.
 
Dave Tolls
Rancher
Posts: 4801
50
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Your given is saying that when save is called with a value equal to ex1 then return whatever that Mono thing is doing.

The code then calls save, but with an Exercise that has an id of <some random UUID> and a filename of <some timestamp>.
That will not equal the given ex1 values.
 
Pete Letkeman
Bartender
Posts: 1868
81
Android IntelliJ IDE MySQL Database Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I think that I'm missing something here.
What if we remove the Mono from the example then we get something like When you explicitly create a value for a mock method as shown are you not telling the framework that when you call that you will get in return?

The ExerciseService calls the myClass.save(item) and the returned value in this instance is a null value for some reason, and the mocked return value is not a null.
 
Dave Tolls
Rancher
Posts: 4801
50
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
What you are telling Mockito with:

is that when save is called with an item that is equal to the given item, then do the return bit.

So Mockito will only react to a call to save that matches the given item.

In your case, the "item" you have told it to match is an Exercise object ex1, which has the values:
"1", "Name #1", "Description #1", "fileName 1.png", true

However your call to save has an Exercise object with the values:
<Some random UUID>, "Name #1", "Description #1",<Some date stamped file name>, true

Those two things are not the same, so Mockito doesn't match them, so falls back to the default return of null.

Now, the question is, do you need to match the actual values (is that part of the test), or is it sufficient to tell Mockito to return the required value whenever save is called with any Exercise object.

If it's the latter then you could use the any(Exercise.class) matcher (check the syntax with the docs).
If it's the former then you may need to write your own as you'll need to only match on certain attributes of Exercise.
 
Pete Letkeman
Bartender
Posts: 1868
81
Android IntelliJ IDE MySQL Database Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Interesting this code/test seems to work: However it does not use the given().willReturn() method(s) attached to the repository.save() method. Plus I replaced the MockBean notation with Autowired.
I suspect that somehow the value of repository.save(ex1) call is being cached and being used/returned when the exerciseService.createExercise(Flux.just(file1), ex1) method is executed.

What Dave previously does make a lot of sense to me about using any(Exercise.class). But when I tried that I still ended up with a NPE.
I suspect that this has to do with repository.save(ex1) not allowing nulls and any(Exercise.class) could be filling the arguments with null values.

One thing is very clear, I still have much to learn with regards to everything that I'm using.
 
Pete Letkeman
Bartender
Posts: 1868
81
Android IntelliJ IDE MySQL Database Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Actually this line is not needed at all
 
Dave Tolls
Rancher
Posts: 4801
50
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Well, that version isn't mocking the repository at all, so I assume the ExerciseRepository is doing its proper work.

The other given() calls are either to a method that has no parameters, so will always match, or has been supplied an any() Matcher, so will also always match.

any(Exercise.class) should work, but not seeing the code that apparently didn't work I can't say what happened there.
 
Pete Letkeman
Bartender
Posts: 1868
81
Android IntelliJ IDE MySQL Database Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator

Dave Tolls wrote:any(Exercise.class) should work, but not seeing the code that apparently didn't work I can't say what happened there.


Translates into:
Which generates the following error message:
ReactiveCrudRepository is a Spring 5/Spring Boot 2 interface.

This Spring 5/Spring Boot 2 and Kotlin are both fairly new as such I suspect that there is something more that need to be done to get this to work.

I'm going to move on with the project and come back to this test and other test which require the use of the repository.save method later on.
Maybe I'll do the testing of these method using Java instead of Kotlin, but that won't be for at least a few days or more.
 
Pete Letkeman
Bartender
Posts: 1868
81
Android IntelliJ IDE MySQL Database Chrome Java
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
To finish this up:

I did end up creating the tests in Java only to find out that I the other programming I did had some issues.
The other programming appeared to be working, but a few assumptions where being made.

Once I fixed the other programming I was able to finish creating my unit tests in Java.
After which I took the tests where were programming in Java and migrated them to Kotlin.

Looks like writing these tests may have saved me from some possible problems in the future.
 
Consider Paul's rocket mass heater.
reply
    Bookmark Topic Watch Topic
  • New Topic