Skip to content

Commit

Permalink
feat: Add a Leaderboard service
Browse files Browse the repository at this point in the history
  • Loading branch information
cjmellor committed Jul 2, 2023
1 parent 749a286 commit 40cc607
Show file tree
Hide file tree
Showing 4 changed files with 75 additions and 2 deletions.
13 changes: 13 additions & 0 deletions src/Facades/Leaderboard.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
<?php

namespace LevelUp\Experience\Facades;

use Illuminate\Support\Facades\Facade;

class Leaderboard extends Facade
{
protected static function getFacadeAccessor(): string
{
return 'leaderboard';
}
}
6 changes: 4 additions & 2 deletions src/LevelUpServiceProvider.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@

use LevelUp\Experience\Providers\EventServiceProvider;
use LevelUp\Experience\Providers\MultiplierServiceProvider;
use LevelUp\Experience\Services\LeaderboardService;
use Spatie\LaravelPackageTools\Package;
use Spatie\LaravelPackageTools\PackageServiceProvider;

Expand All @@ -28,7 +29,8 @@ public function register(): void
{
parent::register();

$this->app->register(EventServiceProvider::class);
$this->app->register(MultiplierServiceProvider::class);
$this->app->register(provider: EventServiceProvider::class);
$this->app->singleton(abstract: 'leaderboard', concrete: fn () => new LeaderboardService());
$this->app->register(provider: MultiplierServiceProvider::class);
}
}
30 changes: 30 additions & 0 deletions src/Services/LeaderboardService.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
<?php

namespace LevelUp\Experience\Services;

use Illuminate\Contracts\Pagination\LengthAwarePaginator;
use Illuminate\Database\Eloquent\Collection;
use LevelUp\Experience\Models\Experience;

class LeaderboardService
{
private mixed $userModel;

public function __construct()
{
$this->userModel = config(key: 'level-up.user.model');
}

public function generate($paginate = false, int|null $limit = null): array|Collection|LengthAwarePaginator
{
return $this->userModel::query()
->with(relations: ['experience', 'level'])
->orderByDesc(
column: Experience::select('experience_points')
->whereColumn('user_id', 'users.id')
->latest()
)
->take($limit)
->when($paginate, fn ($query) => $query->paginate(), fn ($query) => $query->get());
}
}
28 changes: 28 additions & 0 deletions tests/Services/LeaderboardServiceTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
<?php

uses()->group('leaderboard');

use LevelUp\Experience\Services\LeaderboardService;
use LevelUp\Experience\Tests\Fixtures\User;

beforeEach(function () {
config(['level-up.user.model' => User::class]);
config(['level-up.multiplier.enabled' => false]);
});

it(description: 'returns the correct data in the correct order', closure: function () {
// A User is also created in Pest.php, so we have 5 Users in total.
tap(User::newFactory()->create())->addPoints(44);
tap(User::newFactory()->create())->addPoints(123);
tap(User::newFactory()->create())->addPoints(198);
tap(User::newFactory()->create())->addPoints(245);

expect(
app(abstract: LeaderboardService::class)
->generate()
->pluck(value: 'experience.experience_points')
->toArray()
)
->toBe([245, 198, 123, 44, null])
->toHaveCount(count: 5);
});

0 comments on commit 40cc607

Please sign in to comment.