Hi all. I’m trying to mock RestTemplate in a Sprin...
# spring
l
Hi all. I’m trying to mock RestTemplate in a Spring app for testing purposes. The only docs I’ve found for that is this page, which is Java-targeted: https://www.baeldung.com/spring-mock-rest-template However, the expect() call there doesn’t seem to translate to Kotlin very easily. I… have no idea what requestTo() turns into, and IDE autocomplete is not being helpful. Any suggestions on what the Kotlin version of that would be?
j
That article isn't really about mocking resttemplate. It's about mocking the server. If anything you're testing the template to ensure that it's generating the correct requests
And it's just java. No reason I can think of for it not translating to kotlin
https://docs.spring.io/spring-framework/docs/6.1.11/kdoc-api/spring-test/index.html I see kotlin extension functions for other spring mocks but not for the rest template tests. Which makes sense since resttemplate itself is practically deprecated. But the extension functions are just for convenience. You should be able to test using basic java interop
t
did you check the Github repository linked at the bottom of the article? I find it quite annoying when people omit imports in their sample code, but in this case you can see the whole source code, eg: https://github.com/eugenp/tutorials/blob/master/spring-web-modules/spring-resttemp[…]baeldung/mock/EmployeeServiceMockRestServiceServerUnitTest.java that said, we recently migrated to
org.springframework.web.client.RestClient
since
RestTemplate
is kept around in maintenance mode only because it's used a lot, but it has a lot of limitations (like inability to stream), but we had a bunch of test using
MockRestServiceServer
bound to a
RestTemplate
before and did not have any problem
l
@thanksforallthefish Oh! Yes, the lack of imports in examples is super annoying, but that looks like it’s showing some of the pieces I’m missing. Let me see if those help. I know RestTemplate is deprecated; we only just migrated off of Spring Boot 2. 😬 I have a ticket in our queue to upgrade to WebClient, but haven’t gotten there yet, so I’m stuck with this for now. As for translating Java to Kotlin, I’m sure it can be, I’m just not very good at it yet. (Only using Kotlin a few months, and no JVM before that, and when examples don’t show the imports they’re using I have to just kinda guess why “requestTo” is undefined, and such.)
j
FYI spring never implemented any similar testing tool for webclient. They recommended just using a mock server library
l
How does that even work? You stick a fake server behind the real rest client somehow? That seems… complicated. (I’m coming from a PHP background; most HTTP clients in PHP have a very simple interface they support, making mocking/faking it super easy. All this server wrapper stuff is novel to me.)
OK, the imports got me further. It’s recognizing requestTo() now. But requestTo() returns a RequestMatcher instance, and the code is then trying to call
andExpect().andRespond()
on it. Neither of which methods appear to be defined.
t
FYI spring never implemented any similar testing tool for webclient. They recommended just using a mock server library
but they extended
MockRestServiceServer
to support the even newer
RestClient
, so I guess they are still making up their minds, probably based on community feedback. A mock server library, like
Wiremock
or
okhttp3.mockwebserver
would also be an option and it would transparent for future changes (should you remove the
RestTemplate
at some point you would not need to change anything in the test). I find them more cumbersome to use though, but it's probably just a matter of habit
to your problem, it's probably some as simple as wrong parenthesis position,
andExpect
is not a method on the
RequestMatcher
, eg:
Copy code
import org.springframework.test.web.client.match.MockRestRequestMatchers.method
import org.springframework.test.web.client.match.MockRestRequestMatchers.requestTo
import org.springframework.test.web.client.response.MockRestResponseCreators.withSuccess
import org.springframework.http.HttpMethod

server.expect(
  requestTo("...")
)
.andExpect(
  method(HttpMethod.POST)
)
.andRespond(withSuccess())
j
How does that even work? You stick a fake server behind the real rest client somehow? That seems… complicated.
You add a list of canned responses to the server. The server saves every request it gets. You look at the list of requests and assert that they look right.
202 Views