Singleton
In laravel we usually use IoC to build our application, when we call one Class, all dependency in this class will involed.
For testing this class, we can defined depencency in service container as singleton.
Create a service provider:
php artisan make:provider WeatherServiceProvider
In here, using service container register a singleton for decoupling Prepare a singleton
WeatherServiceProvider.php
<?php
namespace App\Providers;
use App\Http\Services\WeatherServices;
use Illuminate\Support\ServiceProvider;
class WeatherServiceProvider extends ServiceProvider
{
/**
* Register services.
*
* @return void
*/
public function register()
{
$this->app->singleton(WeatherServices::class, function($app) : weatherservices {
return new WeatherServices('defalt from singleton');
});
}
/**
* Bootstrap services.
*
* @return void
*/
public function boot()
{
//
}
}
Register your provider on config/app.php
'providers' => [
...
App\Providers\WeatherServiceProvider::class,]
Generate a test for service provider
Make sure the service perovider will call singleton, we make a unittest for this provider:
php artisan make:test WeatherServiceProviderTest
WeatherServiceProviderTest.php
<?php
namespace Tests\Feature;
use Tests\TestCase;
use App\Http\Services\WeatherServices;
use Illuminate\Foundation\Testing\WithFaker;
use Illuminate\Foundation\Testing\RefreshDatabase;
class WeatherServiceProviderTest extends TestCase
{
/**
* A basic feature test example.
*
* @return void
*/
public function testHasRegisterWeatherServiceProviderClassSingleton()
{
$this->assertTrue($this->app->bound(WeatherServices::class));
$actual = $this->app->make(WeatherServices::class);
$exptectd = $this->app->make(WeatherServices::class);
$this->assertSame(
$actual,
$exptectd
);
}
/**
* A basic feature test example.
*
* @return void
*/
public function testHasRegisterWeatherServiceShouldEqualAsSingleton()
{
$exptectd = new WeatherServices('defalt from singleton');
$actual = $this->app->make(WeatherServices::class);
$this->assertEquals(
$exptectd,
$actual
);
}
}
Create a route access weather controller
routes/api.php
Route::get('/hello', [WeatherController::class, 'currentWeather'] );
WeatherController.php
<?php
namespace App\Http\Controllers;
use Carbon\Carbon;
use Illuminate\Http\Request;
use App\Http\Services\WeatherServices;
use App\Exceptions\WeatherNotFoundException;
class weatherController extends Controller
{
protected $users = 'default from controller';
protected $WeatherServices;
public function __construct(WeatherServices $WeatherServices)
{
$this->WeatherServices = $WeatherServices;
}
/**
* current weather
*
* @return void
*/
public function currentWeather($name = '')
{
if($name!=''){
$this->users = $name;
}
try {
$results = $this->WeatherServices->getWeather($this->users);
} catch (WeatherNotFoundException $e) {
report($e);
return false;
}
return $results;
}
}
WeatherServices.php
<?php
namespace App\Http\Services;
use Illuminate\Http\Request;
use App\Exceptions\WeatherNotFoundException;
class WeatherServices
{
protected $users;
public function __construct(string $users = '')
{
$this->users = $users;
}
/**
* Get weather info
*
* @return array
*/
public function getWeather($name='')
{
if ($name!='') {
$this->users = $name;
}
if ($this->users == '') {
throw new WeatherNotFoundException('please input user name');
}
return ['weather'=>'rain', 'user'=>$this->users];
}
}