I want to mock a service who call a third party, but I can't figure it out.
I have a controller method who has a service injected on it and do stuff:
public function store(Request $request, MyService $myService)
{
$data = $request->validated();
$myService->create($data, $request->user());
return response()->json();
}
In this service, I call a job to do other stuffs:
MyJob::dispatch($manager);
My job is built like this:
public function __construct(private Manager $manager)
{
}
public function handle()
{
// THE SERVICE I WANT TO MOCK
$this->managementService = resolve(ManagementService::class, ['manager_id' => $this->manager->id]);
$this->doStuff();
}
private function doStuff() {
$this->managementService->startManagement();
}
In ManagementService I want to mock the function callApi:
public function startManagement()
{
$data = $this->callApi('/thirdparty/call');
return $data;
}
SO, in my test I try to mock the ManagementService and call my route who do all these things
$this->mock(ManagementService::class, function ($mock) {
$mock->shouldReceive('callApi')->andReturn('none');
});
$response = $this->actingAs(User::factory()->create())->post('/myroute', [
'manager_id' => 4,
]);
But it seems this mock is never used, it's still going into the "normal" Management Service, because when I dump $data in the startManagement method when I launch tests, it's not returning 'none'.
What am I doing wrong?
Thanks
CodePudding user response:
The code that you post is not very clear but if i understand correctly you like to mock a hard dependency thats why your mock never called because you never register it.
Just add the string overload
before the class name in the mock method.
CodePudding user response:
Figured it out by injecting my service directly in the job
MyJob::dispatch($manager, resolve(ManagementService::class, ['manager_id' => $this->manager->id]));
And inside the service instance it via constructor instead of in the handle
public function __construct(public Manager $manager, ManagementService $managementService)
{
$this->managementService = $managementService;
}
Then in my test, my mock is instancied like this:
$mock = Mockery::mock(ManagementService::class);
$mock->shouldReceive('callApi')
->once()
->andReturn('none');
Thanks to all