refactor: use attributes for tests (#1858)

This commit is contained in:
Phan An 2024-10-24 17:45:45 +07:00 committed by GitHub
parent 575551c903
commit 793b59e9cf
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
112 changed files with 903 additions and 396 deletions

View file

@ -6,6 +6,7 @@ use App\Models\Album;
use App\Services\MediaMetadataService; use App\Services\MediaMetadataService;
use Mockery; use Mockery;
use Mockery\MockInterface; use Mockery\MockInterface;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
@ -22,7 +23,8 @@ class AlbumCoverTest extends TestCase
$this->mediaMetadataService = self::mock(MediaMetadataService::class); $this->mediaMetadataService = self::mock(MediaMetadataService::class);
} }
public function testUpdate(): void #[Test]
public function update(): void
{ {
$album = Album::factory()->create(); $album = Album::factory()->create();
@ -35,7 +37,8 @@ class AlbumCoverTest extends TestCase
->assertOk(); ->assertOk();
} }
public function testUpdateNotAllowedForNormalUsers(): void #[Test]
public function updateNotAllowedForNormalUsers(): void
{ {
$album = Album::factory()->create(); $album = Album::factory()->create();

View file

@ -6,11 +6,13 @@ use App\Models\Album;
use App\Services\MediaInformationService; use App\Services\MediaInformationService;
use App\Values\AlbumInformation; use App\Values\AlbumInformation;
use Mockery; use Mockery;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class AlbumInformationTest extends TestCase class AlbumInformationTest extends TestCase
{ {
public function testGet(): void #[Test]
public function getInformation(): void
{ {
config(['koel.lastfm.key' => 'foo']); config(['koel.lastfm.key' => 'foo']);
config(['koel.lastfm.secret' => 'geheim']); config(['koel.lastfm.secret' => 'geheim']);
@ -45,7 +47,8 @@ class AlbumInformationTest extends TestCase
->assertJsonStructure(AlbumInformation::JSON_STRUCTURE); ->assertJsonStructure(AlbumInformation::JSON_STRUCTURE);
} }
public function testGetWithoutLastfmStillReturnsValidStructure(): void #[Test]
public function getWithoutLastfmStillReturnsValidStructure(): void
{ {
config(['koel.lastfm.key' => null]); config(['koel.lastfm.key' => null]);
config(['koel.lastfm.secret' => null]); config(['koel.lastfm.secret' => null]);

View file

@ -5,11 +5,13 @@ namespace Tests\Feature;
use App\Http\Resources\SongResource; use App\Http\Resources\SongResource;
use App\Models\Album; use App\Models\Album;
use App\Models\Song; use App\Models\Song;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class AlbumSongTest extends TestCase class AlbumSongTest extends TestCase
{ {
public function testIndex(): void #[Test]
public function index(): void
{ {
$album = Album::factory()->create(); $album = Album::factory()->create();

View file

@ -4,11 +4,13 @@ namespace Tests\Feature;
use App\Http\Resources\AlbumResource; use App\Http\Resources\AlbumResource;
use App\Models\Album; use App\Models\Album;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class AlbumTest extends TestCase class AlbumTest extends TestCase
{ {
public function testIndex(): void #[Test]
public function index(): void
{ {
Album::factory(10)->create(); Album::factory(10)->create();
@ -16,7 +18,8 @@ class AlbumTest extends TestCase
->assertJsonStructure(AlbumResource::PAGINATION_JSON_STRUCTURE); ->assertJsonStructure(AlbumResource::PAGINATION_JSON_STRUCTURE);
} }
public function testShow(): void #[Test]
public function show(): void
{ {
$this->getAs('api/albums/' . Album::factory()->create()->id) $this->getAs('api/albums/' . Album::factory()->create()->id)
->assertJsonStructure(AlbumResource::JSON_STRUCTURE); ->assertJsonStructure(AlbumResource::JSON_STRUCTURE);

View file

@ -6,6 +6,8 @@ use App\Models\Album;
use App\Services\MediaMetadataService; use App\Services\MediaMetadataService;
use Mockery; use Mockery;
use Mockery\MockInterface; use Mockery\MockInterface;
use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class AlbumThumbnailTest extends TestCase class AlbumThumbnailTest extends TestCase
@ -25,8 +27,9 @@ class AlbumThumbnailTest extends TestCase
return [['http://localhost/img/covers/foo_thumbnail.jpg'], [null]]; return [['http://localhost/img/covers/foo_thumbnail.jpg'], [null]];
} }
/** @dataProvider provideAlbumThumbnailData */ #[DataProvider('provideAlbumThumbnailData')]
public function testGetAlbumThumbnail(?string $thumbnailUrl): void #[Test]
public function getAlbumThumbnail(?string $thumbnailUrl): void
{ {
$createdAlbum = Album::factory()->create(); $createdAlbum = Album::factory()->create();

View file

@ -5,11 +5,13 @@ namespace Tests\Feature;
use App\Http\Resources\AlbumResource; use App\Http\Resources\AlbumResource;
use App\Models\Album; use App\Models\Album;
use App\Models\Artist; use App\Models\Artist;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class ArtistAlbumTest extends TestCase class ArtistAlbumTest extends TestCase
{ {
public function testIndex(): void #[Test]
public function index(): void
{ {
$artist = Artist::factory()->create(); $artist = Artist::factory()->create();

View file

@ -6,6 +6,7 @@ use App\Models\Artist;
use App\Services\MediaMetadataService; use App\Services\MediaMetadataService;
use Mockery; use Mockery;
use Mockery\MockInterface; use Mockery\MockInterface;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
@ -21,7 +22,8 @@ class ArtistImageTest extends TestCase
$this->mediaMetadataService = self::mock(MediaMetadataService::class); $this->mediaMetadataService = self::mock(MediaMetadataService::class);
} }
public function testUpdate(): void #[Test]
public function update(): void
{ {
$artist = Artist::factory()->create(); $artist = Artist::factory()->create();
@ -34,7 +36,8 @@ class ArtistImageTest extends TestCase
->assertOk(); ->assertOk();
} }
public function testUpdateNotAllowedForNormalUsers(): void #[Test]
public function updateNotAllowedForNormalUsers(): void
{ {
Artist::factory()->create(['id' => 9999]); Artist::factory()->create(['id' => 9999]);

View file

@ -6,11 +6,13 @@ use App\Models\Artist;
use App\Services\MediaInformationService; use App\Services\MediaInformationService;
use App\Values\ArtistInformation; use App\Values\ArtistInformation;
use Mockery; use Mockery;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class ArtistInformationTest extends TestCase class ArtistInformationTest extends TestCase
{ {
public function testGet(): void #[Test]
public function getInformation(): void
{ {
config(['koel.lastfm.key' => 'foo']); config(['koel.lastfm.key' => 'foo']);
config(['koel.lastfm.secret' => 'geheim']); config(['koel.lastfm.secret' => 'geheim']);
@ -33,7 +35,8 @@ class ArtistInformationTest extends TestCase
->assertJsonStructure(ArtistInformation::JSON_STRUCTURE); ->assertJsonStructure(ArtistInformation::JSON_STRUCTURE);
} }
public function testGetWithoutLastfmStillReturnsValidStructure(): void #[Test]
public function getWithoutLastfmStillReturnsValidStructure(): void
{ {
config(['koel.lastfm.key' => null]); config(['koel.lastfm.key' => null]);
config(['koel.lastfm.secret' => null]); config(['koel.lastfm.secret' => null]);

View file

@ -5,11 +5,13 @@ namespace Tests\Feature;
use App\Http\Resources\SongResource; use App\Http\Resources\SongResource;
use App\Models\Artist; use App\Models\Artist;
use App\Models\Song; use App\Models\Song;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class ArtistSongTest extends TestCase class ArtistSongTest extends TestCase
{ {
public function testIndex(): void #[Test]
public function index(): void
{ {
$artist = Artist::factory()->create(); $artist = Artist::factory()->create();

View file

@ -4,11 +4,13 @@ namespace Tests\Feature;
use App\Http\Resources\ArtistResource; use App\Http\Resources\ArtistResource;
use App\Models\Artist; use App\Models\Artist;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class ArtistTest extends TestCase class ArtistTest extends TestCase
{ {
public function testIndex(): void #[Test]
public function index(): void
{ {
Artist::factory(10)->create(); Artist::factory(10)->create();
@ -16,7 +18,8 @@ class ArtistTest extends TestCase
->assertJsonStructure(ArtistResource::PAGINATION_JSON_STRUCTURE); ->assertJsonStructure(ArtistResource::PAGINATION_JSON_STRUCTURE);
} }
public function testShow(): void #[Test]
public function show(): void
{ {
$this->getAs('api/artists/' . Artist::factory()->create()->id) $this->getAs('api/artists/' . Artist::factory()->create()->id)
->assertJsonStructure(ArtistResource::JSON_STRUCTURE); ->assertJsonStructure(ArtistResource::JSON_STRUCTURE);

View file

@ -4,13 +4,15 @@ namespace Tests\Feature;
use App\Services\AuthenticationService; use App\Services\AuthenticationService;
use Illuminate\Support\Facades\Hash; use Illuminate\Support\Facades\Hash;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class AuthTest extends TestCase class AuthTest extends TestCase
{ {
public function testLogIn(): void #[Test]
public function logIn(): void
{ {
create_user([ create_user([
'email' => 'koel@koel.dev', 'email' => 'koel@koel.dev',
@ -34,7 +36,8 @@ class AuthTest extends TestCase
->assertUnauthorized(); ->assertUnauthorized();
} }
public function testLoginViaOneTimeToken(): void #[Test]
public function loginViaOneTimeToken(): void
{ {
$user = create_user(); $user = create_user();
$authService = app(AuthenticationService::class); $authService = app(AuthenticationService::class);
@ -48,7 +51,8 @@ class AuthTest extends TestCase
]); ]);
} }
public function testLogOut(): void #[Test]
public function logOut(): void
{ {
$user = create_user([ $user = create_user([
'email' => 'koel@koel.dev', 'email' => 'koel@koel.dev',

View file

@ -11,6 +11,7 @@ use App\Services\DownloadService;
use Illuminate\Support\Collection; use Illuminate\Support\Collection;
use Mockery; use Mockery;
use Mockery\MockInterface; use Mockery\MockInterface;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
@ -27,7 +28,8 @@ class DownloadTest extends TestCase
$this->downloadService = self::mock(DownloadService::class); $this->downloadService = self::mock(DownloadService::class);
} }
public function testNonLoggedInUserCannotDownload(): void #[Test]
public function nonLoggedInUserCannotDownload(): void
{ {
$this->downloadService->shouldNotReceive('getDownloadablePath'); $this->downloadService->shouldNotReceive('getDownloadablePath');
@ -35,7 +37,8 @@ class DownloadTest extends TestCase
->assertUnauthorized(); ->assertUnauthorized();
} }
public function testDownloadOneSong(): void #[Test]
public function downloadOneSong(): void
{ {
$song = Song::factory()->create(); $song = Song::factory()->create();
$user = create_user(); $user = create_user();
@ -52,7 +55,8 @@ class DownloadTest extends TestCase
->assertOk(); ->assertOk();
} }
public function testDownloadMultipleSongs(): void #[Test]
public function downloadMultipleSongs(): void
{ {
$songs = Song::factory(2)->create(); $songs = Song::factory(2)->create();
$user = create_user(); $user = create_user();
@ -74,7 +78,8 @@ class DownloadTest extends TestCase
->assertOk(); ->assertOk();
} }
public function testDownloadAlbum(): void #[Test]
public function downloadAlbum(): void
{ {
$album = Album::factory()->create(); $album = Album::factory()->create();
$songs = Song::factory(3)->for($album)->create(); $songs = Song::factory(3)->for($album)->create();
@ -94,7 +99,8 @@ class DownloadTest extends TestCase
->assertOk(); ->assertOk();
} }
public function testDownloadArtist(): void #[Test]
public function downloadArtist(): void
{ {
$artist = Artist::factory()->create(); $artist = Artist::factory()->create();
$songs = Song::factory(3)->for($artist)->create(); $songs = Song::factory(3)->for($artist)->create();
@ -114,7 +120,8 @@ class DownloadTest extends TestCase
->assertOk(); ->assertOk();
} }
public function testDownloadPlaylist(): void #[Test]
public function downloadPlaylist(): void
{ {
$user = create_user(); $user = create_user();
$songs = Song::factory(3)->create(); $songs = Song::factory(3)->create();
@ -137,7 +144,8 @@ class DownloadTest extends TestCase
->assertOk(); ->assertOk();
} }
public function testNonOwnerCannotDownloadPlaylist(): void #[Test]
public function nonOwnerCannotDownloadPlaylist(): void
{ {
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -145,7 +153,8 @@ class DownloadTest extends TestCase
->assertForbidden(); ->assertForbidden();
} }
public function testDownloadFavorites(): void #[Test]
public function downloadFavorites(): void
{ {
$user = create_user(); $user = create_user();
$favorites = Interaction::factory(3)->for($user)->create(['liked' => true]); $favorites = Interaction::factory(3)->for($user)->create(['liked' => true]);

View file

@ -10,13 +10,15 @@ use App\Models\Album;
use App\Models\Artist; use App\Models\Artist;
use App\Models\Podcast; use App\Models\Podcast;
use App\Models\Song; use App\Models\Song;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class ExcerptSearchTest extends TestCase class ExcerptSearchTest extends TestCase
{ {
public function testSearch(): void #[Test]
public function search(): void
{ {
Song::factory()->create(['title' => 'A Foo Song']); Song::factory()->create(['title' => 'A Foo Song']);
Song::factory(6)->create(); Song::factory(6)->create();

View file

@ -4,13 +4,15 @@ namespace Tests\Feature;
use App\Http\Resources\SongResource; use App\Http\Resources\SongResource;
use App\Models\Interaction; use App\Models\Interaction;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class FavoriteSongTest extends TestCase class FavoriteSongTest extends TestCase
{ {
public function testIndex(): void #[Test]
public function index(): void
{ {
$user = create_user(); $user = create_user();
Interaction::factory(5)->for($user)->create(['liked' => true]); Interaction::factory(5)->for($user)->create(['liked' => true]);

View file

@ -7,13 +7,15 @@ use Illuminate\Auth\Events\PasswordReset;
use Illuminate\Support\Facades\Event; use Illuminate\Support\Facades\Event;
use Illuminate\Support\Facades\Hash; use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Password; use Illuminate\Support\Facades\Password;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class ForgotPasswordTest extends TestCase class ForgotPasswordTest extends TestCase
{ {
public function testSendResetPasswordRequest(): void #[Test]
public function sendResetPasswordRequest(): void
{ {
$this->mock(AuthenticationService::class) $this->mock(AuthenticationService::class)
->shouldReceive('trySendResetPasswordLink') ->shouldReceive('trySendResetPasswordLink')
@ -24,7 +26,8 @@ class ForgotPasswordTest extends TestCase
->assertNoContent(); ->assertNoContent();
} }
public function testSendResetPasswordRequestFailed(): void #[Test]
public function sendResetPasswordRequestFailed(): void
{ {
$this->mock(AuthenticationService::class) $this->mock(AuthenticationService::class)
->shouldReceive('trySendResetPasswordLink') ->shouldReceive('trySendResetPasswordLink')
@ -35,7 +38,8 @@ class ForgotPasswordTest extends TestCase
->assertNotFound(); ->assertNotFound();
} }
public function testResetPassword(): void #[Test]
public function resetPassword(): void
{ {
Event::fake(); Event::fake();
$user = create_user(); $user = create_user();
@ -50,7 +54,8 @@ class ForgotPasswordTest extends TestCase
Event::assertDispatched(PasswordReset::class); Event::assertDispatched(PasswordReset::class);
} }
public function testResetPasswordFailed(): void #[Test]
public function resetPasswordFailed(): void
{ {
Event::fake(); Event::fake();
$user = create_user(['password' => Hash::make('old-password')]); $user = create_user(['password' => Hash::make('old-password')]);

View file

@ -6,11 +6,13 @@ use App\Http\Resources\GenreResource;
use App\Http\Resources\SongResource; use App\Http\Resources\SongResource;
use App\Models\Song; use App\Models\Song;
use App\Values\Genre; use App\Values\Genre;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class GenreTest extends TestCase class GenreTest extends TestCase
{ {
public function testGetAllGenres(): void #[Test]
public function getAllGenres(): void
{ {
Song::factory()->count(5)->create(['genre' => 'Rock']); Song::factory()->count(5)->create(['genre' => 'Rock']);
Song::factory()->count(2)->create(['genre' => 'Pop']); Song::factory()->count(2)->create(['genre' => 'Pop']);
@ -23,7 +25,8 @@ class GenreTest extends TestCase
->assertJsonFragment(['name' => Genre::NO_GENRE, 'song_count' => 10]); ->assertJsonFragment(['name' => Genre::NO_GENRE, 'song_count' => 10]);
} }
public function testGetOneGenre(): void #[Test]
public function getOneGenre(): void
{ {
Song::factory()->count(5)->create(['genre' => 'Rock']); Song::factory()->count(5)->create(['genre' => 'Rock']);
@ -32,12 +35,14 @@ class GenreTest extends TestCase
->assertJsonFragment(['name' => 'Rock', 'song_count' => 5]); ->assertJsonFragment(['name' => 'Rock', 'song_count' => 5]);
} }
public function testGetNonExistingGenreThrowsNotFound(): void #[Test]
public function getNonExistingGenreThrowsNotFound(): void
{ {
$this->getAs('api/genres/NonExistingGenre')->assertNotFound(); $this->getAs('api/genres/NonExistingGenre')->assertNotFound();
} }
public function testPaginateSongsInGenre(): void #[Test]
public function paginateSongsInGenre(): void
{ {
Song::factory()->count(5)->create(['genre' => 'Rock']); Song::factory()->count(5)->create(['genre' => 'Rock']);
@ -45,7 +50,8 @@ class GenreTest extends TestCase
->assertJsonStructure(SongResource::PAGINATION_JSON_STRUCTURE); ->assertJsonStructure(SongResource::PAGINATION_JSON_STRUCTURE);
} }
public function testGetRandomSongsInGenre(): void #[Test]
public function getRandomSongsInGenre(): void
{ {
Song::factory()->count(5)->create(['genre' => 'Rock']); Song::factory()->count(5)->create(['genre' => 'Rock']);

View file

@ -2,11 +2,13 @@
namespace Tests\Feature; namespace Tests\Feature;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class InitialDataTest extends TestCase class InitialDataTest extends TestCase
{ {
public function testIndex(): void #[Test]
public function index(): void
{ {
$this->getAs('/api/data')->assertJsonStructure([ $this->getAs('/api/data')->assertJsonStructure([
'settings', 'settings',

View file

@ -8,13 +8,15 @@ use App\Events\SongLikeToggled;
use App\Models\Interaction; use App\Models\Interaction;
use App\Models\Song; use App\Models\Song;
use Illuminate\Support\Facades\Event; use Illuminate\Support\Facades\Event;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class InteractionTest extends TestCase class InteractionTest extends TestCase
{ {
public function testIncreasePlayCount(): void #[Test]
public function increasePlayCount(): void
{ {
Event::fake(PlaybackStarted::class); Event::fake(PlaybackStarted::class);
@ -39,7 +41,8 @@ class InteractionTest extends TestCase
]); ]);
} }
public function testToggleLike(): void #[Test]
public function toggleLike(): void
{ {
Event::fake(SongLikeToggled::class); Event::fake(SongLikeToggled::class);
@ -66,7 +69,8 @@ class InteractionTest extends TestCase
Event::assertDispatched(SongLikeToggled::class); Event::assertDispatched(SongLikeToggled::class);
} }
public function testToggleLikeBatch(): void #[Test]
public function toggleLikeBatch(): void
{ {
Event::fake(MultipleSongsLiked::class); Event::fake(MultipleSongsLiked::class);

View file

@ -7,6 +7,7 @@ use App\Models\Song;
use App\Services\MediaMetadataService; use App\Services\MediaMetadataService;
use Mockery; use Mockery;
use Mockery\MockInterface; use Mockery\MockInterface;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_admin; use function Tests\create_admin;
@ -23,7 +24,8 @@ class AlbumCoverTest extends PlusTestCase
$this->mediaMetadataService = self::mock(MediaMetadataService::class); $this->mediaMetadataService = self::mock(MediaMetadataService::class);
} }
public function testNormalUserCanUploadCoverIfOwningAllSongsInAlbum(): void #[Test]
public function normalUserCanUploadCoverIfOwningAllSongsInAlbum(): void
{ {
$user = create_user(); $user = create_user();
@ -40,7 +42,8 @@ class AlbumCoverTest extends PlusTestCase
->assertOk(); ->assertOk();
} }
public function testNormalUserCannotUploadCoverIfNotOwningAllSongsInAlbum(): void #[Test]
public function normalUserCannotUploadCoverIfNotOwningAllSongsInAlbum(): void
{ {
$user = create_user(); $user = create_user();
@ -57,7 +60,8 @@ class AlbumCoverTest extends PlusTestCase
->assertForbidden(); ->assertForbidden();
} }
public function testAdminCanUploadCoverEvenIfNotOwningAllSongsInAlbum(): void #[Test]
public function adminCanUploadCoverEvenIfNotOwningAllSongsInAlbum(): void
{ {
$user = create_user(); $user = create_user();

View file

@ -7,6 +7,7 @@ use App\Models\Song;
use App\Services\MediaMetadataService; use App\Services\MediaMetadataService;
use Mockery; use Mockery;
use Mockery\MockInterface; use Mockery\MockInterface;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_admin; use function Tests\create_admin;
@ -23,7 +24,8 @@ class ArtistImageTest extends PlusTestCase
$this->mediaMetadataService = self::mock(MediaMetadataService::class); $this->mediaMetadataService = self::mock(MediaMetadataService::class);
} }
public function testNormalUserCanUploadImageIfOwningAllSongsInArtist(): void #[Test]
public function normalUserCanUploadImageIfOwningAllSongsInArtist(): void
{ {
$user = create_user(); $user = create_user();
@ -40,7 +42,8 @@ class ArtistImageTest extends PlusTestCase
->assertOk(); ->assertOk();
} }
public function testNormalUserCannotUploadImageIfNotOwningAllSongsInArtist(): void #[Test]
public function normalUserCannotUploadImageIfNotOwningAllSongsInArtist(): void
{ {
$user = create_user(); $user = create_user();
@ -57,7 +60,8 @@ class ArtistImageTest extends PlusTestCase
->assertForbidden(); ->assertForbidden();
} }
public function testAdminCanUploadImageEvenIfNotOwningAllSongsInArtist(): void #[Test]
public function adminCanUploadImageEvenIfNotOwningAllSongsInArtist(): void
{ {
$user = create_user(); $user = create_user();

View file

@ -4,6 +4,7 @@ namespace Tests\Feature\KoelPlus;
use App\Models\Song; use App\Models\Song;
use App\Services\DownloadService; use App\Services\DownloadService;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
@ -11,7 +12,8 @@ use function Tests\test_path;
class DownloadTest extends PlusTestCase class DownloadTest extends PlusTestCase
{ {
public function testDownloadPolicy(): void #[Test]
public function downloadPolicy(): void
{ {
$owner = create_user(); $owner = create_user();
$apiToken = $owner->createToken('Koel')->plainTextToken; $apiToken = $owner->createToken('Koel')->plainTextToken;

View file

@ -8,13 +8,15 @@ use App\Events\SongLikeToggled;
use App\Models\Song; use App\Models\Song;
use Illuminate\Support\Collection; use Illuminate\Support\Collection;
use Illuminate\Support\Facades\Event; use Illuminate\Support\Facades\Event;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
class InteractionTest extends PlusTestCase class InteractionTest extends PlusTestCase
{ {
public function testPolicyForRegisterPlay(): void #[Test]
public function policyForRegisterPlay(): void
{ {
Event::fake(SongLikeToggled::class); Event::fake(SongLikeToggled::class);
@ -39,7 +41,8 @@ class InteractionTest extends PlusTestCase
->assertSuccessful(); ->assertSuccessful();
} }
public function testPolicyForToggleLike(): void #[Test]
public function policyForToggleLike(): void
{ {
Event::fake(SongLikeToggled::class); Event::fake(SongLikeToggled::class);
@ -64,7 +67,8 @@ class InteractionTest extends PlusTestCase
->assertSuccessful(); ->assertSuccessful();
} }
public function testPolicyForBatchLike(): void #[Test]
public function policyForBatchLike(): void
{ {
Event::fake(MultipleSongsLiked::class); Event::fake(MultipleSongsLiked::class);
@ -94,7 +98,8 @@ class InteractionTest extends PlusTestCase
->assertForbidden(); ->assertForbidden();
} }
public function testPolicyForBatchUnlike(): void #[Test]
public function policyForBatchUnlike(): void
{ {
Event::fake(MultipleSongsUnliked::class); Event::fake(MultipleSongsUnliked::class);

View file

@ -6,13 +6,15 @@ use App\Http\Resources\PlaylistCollaborationTokenResource;
use App\Http\Resources\PlaylistResource; use App\Http\Resources\PlaylistResource;
use App\Models\Playlist; use App\Models\Playlist;
use App\Models\PlaylistCollaborationToken; use App\Models\PlaylistCollaborationToken;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
class PlaylistCollaborationTest extends PlusTestCase class PlaylistCollaborationTest extends PlusTestCase
{ {
public function testCreatePlaylistCollaborationToken(): void #[Test]
public function createPlaylistCollaborationToken(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -21,7 +23,8 @@ class PlaylistCollaborationTest extends PlusTestCase
->assertJsonStructure(PlaylistCollaborationTokenResource::JSON_STRUCTURE); ->assertJsonStructure(PlaylistCollaborationTokenResource::JSON_STRUCTURE);
} }
public function testAcceptPlaylistCollaborationViaToken(): void #[Test]
public function acceptPlaylistCollaborationViaToken(): void
{ {
/** @var PlaylistCollaborationToken $token */ /** @var PlaylistCollaborationToken $token */
$token = PlaylistCollaborationToken::factory()->create(); $token = PlaylistCollaborationToken::factory()->create();

View file

@ -3,13 +3,15 @@
namespace Tests\Feature\KoelPlus; namespace Tests\Feature\KoelPlus;
use App\Models\Playlist; use App\Models\Playlist;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
class PlaylistCoverTest extends PlusTestCase class PlaylistCoverTest extends PlusTestCase
{ {
public function testCollaboratorCanNotUploadCover(): void #[Test]
public function collaboratorCanNotUploadCover(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -20,7 +22,8 @@ class PlaylistCoverTest extends PlusTestCase
->assertForbidden(); ->assertForbidden();
} }
public function testCollaboratorCannotDeleteCover(): void #[Test]
public function collaboratorCannotDeleteCover(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();

View file

@ -4,13 +4,15 @@ namespace Tests\Feature\KoelPlus;
use App\Models\Playlist; use App\Models\Playlist;
use App\Models\PlaylistFolder; use App\Models\PlaylistFolder;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
class PlaylistFolderTest extends PlusTestCase class PlaylistFolderTest extends PlusTestCase
{ {
public function testCollaboratorPuttingPlaylistIntoTheirFolder(): void #[Test]
public function collaboratorPuttingPlaylistIntoTheirFolder(): void
{ {
$collaborator = create_user(); $collaborator = create_user();
@ -40,7 +42,8 @@ class PlaylistFolderTest extends PlusTestCase
self::assertTrue($playlist->fresh()->getFolder($playlist->user)?->is($ownerFolder)); self::assertTrue($playlist->fresh()->getFolder($playlist->user)?->is($ownerFolder));
} }
public function testCollaboratorMovingPlaylistToRootLevel(): void #[Test]
public function collaboratorMovingPlaylistToRootLevel(): void
{ {
$collaborator = create_user(); $collaborator = create_user();

View file

@ -5,13 +5,15 @@ namespace Tests\Feature\KoelPlus;
use App\Http\Resources\CollaborativeSongResource; use App\Http\Resources\CollaborativeSongResource;
use App\Models\Playlist; use App\Models\Playlist;
use App\Models\Song; use App\Models\Song;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
class PlaylistSongTest extends PlusTestCase class PlaylistSongTest extends PlusTestCase
{ {
public function testGetSongsInCollaborativePlaylist(): void #[Test]
public function getSongsInCollaborativePlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -26,7 +28,8 @@ class PlaylistSongTest extends PlusTestCase
->assertJsonCount(3); ->assertJsonCount(3);
} }
public function testPrivateSongsDoNotShowUpInCollaborativePlaylist(): void #[Test]
public function privateSongsDoNotShowUpInCollaborativePlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -46,7 +49,8 @@ class PlaylistSongTest extends PlusTestCase
->assertJsonMissing(['id' => $privateSong->id]); ->assertJsonMissing(['id' => $privateSong->id]);
} }
public function testCollaboratorCanAddSongs(): void #[Test]
public function collaboratorCanAddSongs(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -61,7 +65,8 @@ class PlaylistSongTest extends PlusTestCase
$songs->each(static fn (Song $song) => self::assertTrue($playlist->playables->contains($song))); $songs->each(static fn (Song $song) => self::assertTrue($playlist->playables->contains($song)));
} }
public function testCollaboratorCanRemoveSongs(): void #[Test]
public function collaboratorCanRemoveSongs(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();

View file

@ -5,13 +5,15 @@ namespace Tests\Feature\KoelPlus;
use App\Http\Resources\PlaylistResource; use App\Http\Resources\PlaylistResource;
use App\Models\Playlist; use App\Models\Playlist;
use App\Values\SmartPlaylistRule; use App\Values\SmartPlaylistRule;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
class PlaylistTest extends PlusTestCase class PlaylistTest extends PlusTestCase
{ {
public function testCreatingPlaylistWithOwnSongsOnlyOption(): void #[Test]
public function creatingPlaylistWithOwnSongsOnlyOption(): void
{ {
$user = create_user(); $user = create_user();
@ -44,7 +46,8 @@ class PlaylistTest extends PlusTestCase
self::assertTrue($playlist->own_songs_only); self::assertTrue($playlist->own_songs_only);
} }
public function testUpdatePlaylistWithOwnSongsOnlyOption(): void #[Test]
public function updatePlaylistWithOwnSongsOnlyOption(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->smart()->create(); $playlist = Playlist::factory()->smart()->create();
@ -61,7 +64,8 @@ class PlaylistTest extends PlusTestCase
self::assertTrue($playlist->own_songs_only); self::assertTrue($playlist->own_songs_only);
} }
public function testCollaboratorCannotChangePlaylistName(): void #[Test]
public function collaboratorCannotChangePlaylistName(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();

View file

@ -2,6 +2,7 @@
namespace Tests\Feature\KoelPlus; namespace Tests\Feature\KoelPlus;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
@ -10,7 +11,8 @@ use function Tests\test_path;
class ProfileTest extends PlusTestCase class ProfileTest extends PlusTestCase
{ {
public function testUpdateSSOProfile(): void #[Test]
public function updateSSOProfile(): void
{ {
$user = create_user([ $user = create_user([
'sso_provider' => 'Google', 'sso_provider' => 'Google',

View file

@ -4,6 +4,7 @@ namespace Tests\Feature\KoelPlus;
use App\Models\User; use App\Models\User;
use Laravel\Sanctum\PersonalAccessToken; use Laravel\Sanctum\PersonalAccessToken;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
@ -34,7 +35,8 @@ class ProxyAuthTest extends PlusTestCase
parent::tearDown(); parent::tearDown();
} }
public function testProxyAuthenticateNewUser(): void #[Test]
public function proxyAuthenticateNewUser(): void
{ {
$response = $this->get('/', [ $response = $this->get('/', [
'REMOTE_ADDR' => '192.168.1.127', 'REMOTE_ADDR' => '192.168.1.127',
@ -58,7 +60,8 @@ class ProxyAuthTest extends PlusTestCase
]); ]);
} }
public function testProxyAuthenticateExistingUser(): void #[Test]
public function proxyAuthenticateExistingUser(): void
{ {
$user = create_user([ $user = create_user([
'sso_id' => '123456', 'sso_id' => '123456',
@ -80,7 +83,8 @@ class ProxyAuthTest extends PlusTestCase
self::assertTrue($user->is(PersonalAccessToken::findToken($token['token'])->tokenable)); self::assertTrue($user->is(PersonalAccessToken::findToken($token['token'])->tokenable));
} }
public function testProxyAuthenticateWithDisallowedIp(): void #[Test]
public function proxyAuthenticateWithDisallowedIp(): void
{ {
$response = $this->get('/', [ $response = $this->get('/', [
'REMOTE_ADDR' => '255.168.1.127', 'REMOTE_ADDR' => '255.168.1.127',

View file

@ -6,13 +6,15 @@ use Illuminate\Support\Str;
use Laravel\Socialite\Facades\Socialite; use Laravel\Socialite\Facades\Socialite;
use Laravel\Socialite\Two\User as GoogleUser; use Laravel\Socialite\Two\User as GoogleUser;
use Mockery; use Mockery;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
class GoogleTest extends PlusTestCase class GoogleTest extends PlusTestCase
{ {
public function testCallbackWithNewUser(): void #[Test]
public function callbackWithNewUser(): void
{ {
$googleUser = Mockery::mock(GoogleUser::class, [ $googleUser = Mockery::mock(GoogleUser::class, [
'getEmail' => 'bruce@iron.com', 'getEmail' => 'bruce@iron.com',
@ -29,7 +31,8 @@ class GoogleTest extends PlusTestCase
$response->assertViewHas('token'); $response->assertViewHas('token');
} }
public function testCallbackWithExistingEmail(): void #[Test]
public function callbackWithExistingEmail(): void
{ {
create_user(['email' => 'bruce@iron.com']); create_user(['email' => 'bruce@iron.com']);
@ -48,7 +51,8 @@ class GoogleTest extends PlusTestCase
$response->assertViewHas('token'); $response->assertViewHas('token');
} }
public function testCallbackWithExistingSSOUser(): void #[Test]
public function callbackWithExistingSSOUser(): void
{ {
create_user([ create_user([
'sso_provider' => 'Google', 'sso_provider' => 'Google',

View file

@ -6,6 +6,7 @@ use App\Models\Song;
use App\Services\Streamer\Adapters\LocalStreamerAdapter; use App\Services\Streamer\Adapters\LocalStreamerAdapter;
use App\Services\TokenManager; use App\Services\TokenManager;
use App\Values\CompositeToken; use App\Values\CompositeToken;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
@ -13,7 +14,8 @@ use function Tests\test_path;
class SongPlayTest extends PlusTestCase class SongPlayTest extends PlusTestCase
{ {
public function testPlayPublicUnownedSong(): void #[Test]
public function playPublicUnownedSong(): void
{ {
/** @var CompositeToken $token */ /** @var CompositeToken $token */
$token = app(TokenManager::class)->createCompositeToken(create_user()); $token = app(TokenManager::class)->createCompositeToken(create_user());
@ -31,7 +33,8 @@ class SongPlayTest extends PlusTestCase
->assertOk(); ->assertOk();
} }
public function testPlayPrivateOwnedSong(): void #[Test]
public function playPrivateOwnedSong(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->private()->create([ $song = Song::factory()->private()->create([
@ -49,7 +52,8 @@ class SongPlayTest extends PlusTestCase
->assertOk(); ->assertOk();
} }
public function testCannotPlayPrivateUnownedSong(): void #[Test]
public function cannotPlayPrivateUnownedSong(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->private()->create([ $song = Song::factory()->private()->create([

View file

@ -4,13 +4,15 @@ namespace Tests\Feature\KoelPlus;
use App\Models\Song; use App\Models\Song;
use Illuminate\Support\Collection; use Illuminate\Support\Collection;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
class SongTest extends PlusTestCase class SongTest extends PlusTestCase
{ {
public function testWithOwnSongsOnlyOptionOn(): void #[Test]
public function withOwnSongsOnlyOptionOn(): void
{ {
$user = create_user(); $user = create_user();
@ -27,7 +29,8 @@ class SongTest extends PlusTestCase
->assertJsonFragment(['id' => $ownSongs[2]->id]); ->assertJsonFragment(['id' => $ownSongs[2]->id]);
} }
public function testWithOwnSongsOnlyOptionOffOrMissing(): void #[Test]
public function withOwnSongsOnlyOptionOffOrMissing(): void
{ {
$user = create_user(); $user = create_user();
@ -43,7 +46,8 @@ class SongTest extends PlusTestCase
->assertJsonCount(5, 'data'); ->assertJsonCount(5, 'data');
} }
public function testShowSongPolicy(): void #[Test]
public function showSongPolicy(): void
{ {
$user = create_user(); $user = create_user();
@ -66,7 +70,8 @@ class SongTest extends PlusTestCase
$this->getAs("api/songs/$externalUnownedSong->id", $user)->assertForbidden(); $this->getAs("api/songs/$externalUnownedSong->id", $user)->assertForbidden();
} }
public function testEditSongsPolicy(): void #[Test]
public function editSongsPolicy(): void
{ {
$currentUser = create_user(); $currentUser = create_user();
$anotherUser = create_user(); $anotherUser = create_user();
@ -103,7 +108,8 @@ class SongTest extends PlusTestCase
], $currentUser)->assertSuccessful(); ], $currentUser)->assertSuccessful();
} }
public function testDeleteSongsPolicy(): void #[Test]
public function deleteSongsPolicy(): void
{ {
$currentUser = create_user(); $currentUser = create_user();
$anotherUser = create_user(); $anotherUser = create_user();
@ -128,7 +134,8 @@ class SongTest extends PlusTestCase
->assertSuccessful(); ->assertSuccessful();
} }
public function testPublicizeSongs(): void #[Test]
public function publicizeSongs(): void
{ {
$user = create_user(); $user = create_user();
@ -144,7 +151,8 @@ class SongTest extends PlusTestCase
}); });
} }
public function testPrivatizeSongs(): void #[Test]
public function privatizeSongs(): void
{ {
$user = create_user(); $user = create_user();
@ -160,7 +168,8 @@ class SongTest extends PlusTestCase
}); });
} }
public function testPublicizingOrPrivatizingSongsRequiresOwnership(): void #[Test]
public function publicizingOrPrivatizingSongsRequiresOwnership(): void
{ {
$songs = Song::factory(3)->public()->create(); $songs = Song::factory(3)->public()->create();

View file

@ -4,13 +4,15 @@ namespace Tests\Feature\KoelPlus;
use App\Models\Song; use App\Models\Song;
use Illuminate\Support\Collection; use Illuminate\Support\Collection;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
class SongVisibilityTest extends PlusTestCase class SongVisibilityTest extends PlusTestCase
{ {
public function testMakingSongPublic(): void #[Test]
public function makingSongPublic(): void
{ {
$currentUser = create_user(); $currentUser = create_user();
$anotherUser = create_user(); $anotherUser = create_user();
@ -31,7 +33,8 @@ class SongVisibilityTest extends PlusTestCase
$ownSongs->each(static fn (Song $song) => self::assertTrue($song->refresh()->is_public)); $ownSongs->each(static fn (Song $song) => self::assertTrue($song->refresh()->is_public));
} }
public function testMakingSongPrivate(): void #[Test]
public function makingSongPrivate(): void
{ {
$currentUser = create_user(); $currentUser = create_user();
$anotherUser = create_user(); $anotherUser = create_user();

View file

@ -5,6 +5,7 @@ namespace Tests\Feature\KoelPlus;
use App\Models\Setting; use App\Models\Setting;
use App\Models\Song; use App\Models\Song;
use Illuminate\Http\UploadedFile; use Illuminate\Http\UploadedFile;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
@ -22,7 +23,8 @@ class UploadTest extends PlusTestCase
$this->file = UploadedFile::fromFile(test_path('songs/full.mp3'), 'song.mp3'); //@phpstan-ignore-line $this->file = UploadedFile::fromFile(test_path('songs/full.mp3'), 'song.mp3'); //@phpstan-ignore-line
} }
public function testUploads(): void #[Test]
public function uploads(): void
{ {
$user = create_user(); $user = create_user();

View file

@ -7,13 +7,15 @@ use App\Services\TokenManager;
use Laravel\Sanctum\NewAccessToken; use Laravel\Sanctum\NewAccessToken;
use Laravel\Sanctum\PersonalAccessToken; use Laravel\Sanctum\PersonalAccessToken;
use Mockery; use Mockery;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class LastfmTest extends TestCase class LastfmTest extends TestCase
{ {
public function testSetSessionKey(): void #[Test]
public function setSessionKey(): void
{ {
$user = create_user(); $user = create_user();
$this->postAs('api/lastfm/session-key', ['key' => 'foo'], $user) $this->postAs('api/lastfm/session-key', ['key' => 'foo'], $user)
@ -22,7 +24,8 @@ class LastfmTest extends TestCase
self::assertSame('foo', $user->refresh()->preferences->lastFmSessionKey); self::assertSame('foo', $user->refresh()->preferences->lastFmSessionKey);
} }
public function testConnectToLastfm(): void #[Test]
public function connectToLastfm(): void
{ {
$user = create_user(); $user = create_user();
$token = $user->createToken('Koel')->plainTextToken; $token = $user->createToken('Koel')->plainTextToken;
@ -47,6 +50,7 @@ class LastfmTest extends TestCase
); );
} }
#[Test]
public function testCallback(): void public function testCallback(): void
{ {
$user = create_user(); $user = create_user();
@ -71,7 +75,8 @@ class LastfmTest extends TestCase
self::assertNull(PersonalAccessToken::findToken($token)); self::assertNull(PersonalAccessToken::findToken($token));
} }
public function testRetrieveAndStoreSessionKey(): void #[Test]
public function retrieveAndStoreSessionKey(): void
{ {
$user = create_user(); $user = create_user();
@ -96,7 +101,8 @@ class LastfmTest extends TestCase
self::assertSame('my-session-key', $user->refresh()->preferences->lastFmSessionKey); self::assertSame('my-session-key', $user->refresh()->preferences->lastFmSessionKey);
} }
public function testDisconnectUser(): void #[Test]
public function disconnectUser(): void
{ {
$user = create_user(); $user = create_user();
self::assertNotNull($user->preferences->lastFmSessionKey); self::assertNotNull($user->preferences->lastFmSessionKey);

View file

@ -4,6 +4,7 @@ namespace Tests\Feature\ObjectStorage;
use App\Models\Song; use App\Models\Song;
use Illuminate\Foundation\Testing\WithoutMiddleware; use Illuminate\Foundation\Testing\WithoutMiddleware;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
@ -22,7 +23,8 @@ class S3Test extends TestCase
create_admin(); create_admin();
} }
public function testStoringASong(): void #[Test]
public function storingASong(): void
{ {
$this->post('api/os/s3/song', [ $this->post('api/os/s3/song', [
'bucket' => 'koel', 'bucket' => 'koel',
@ -48,7 +50,8 @@ class S3Test extends TestCase
self::assertSame(5, $song->track); self::assertSame(5, $song->track);
} }
public function testRemovingASong(): void #[Test]
public function removingASong(): void
{ {
Song::factory()->create([ Song::factory()->create([
'path' => 's3://koel/sample.mp3', 'path' => 's3://koel/sample.mp3',

View file

@ -6,13 +6,15 @@ use App\Http\Resources\AlbumResource;
use App\Http\Resources\ArtistResource; use App\Http\Resources\ArtistResource;
use App\Http\Resources\SongResource; use App\Http\Resources\SongResource;
use App\Models\Interaction; use App\Models\Interaction;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class OverviewTest extends TestCase class OverviewTest extends TestCase
{ {
public function testIndex(): void #[Test]
public function index(): void
{ {
$user = create_user(); $user = create_user();

View file

@ -6,13 +6,15 @@ use App\Events\PlaybackStarted;
use App\Models\Interaction; use App\Models\Interaction;
use App\Models\Song; use App\Models\Song;
use Illuminate\Support\Facades\Event; use Illuminate\Support\Facades\Event;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class PlayCountTest extends TestCase class PlayCountTest extends TestCase
{ {
public function testStoreExistingEntry(): void #[Test]
public function storeExistingEntry(): void
{ {
Event::fake(PlaybackStarted::class); Event::fake(PlaybackStarted::class);
@ -33,7 +35,8 @@ class PlayCountTest extends TestCase
Event::assertDispatched(PlaybackStarted::class); Event::assertDispatched(PlaybackStarted::class);
} }
public function testStoreNewEntry(): void #[Test]
public function storeNewEntry(): void
{ {
Event::fake(PlaybackStarted::class); Event::fake(PlaybackStarted::class);

View file

@ -3,6 +3,7 @@
namespace Tests\Feature; namespace Tests\Feature;
use App\Models\Playlist; use App\Models\Playlist;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
@ -11,7 +12,8 @@ use function Tests\test_path;
class PlaylistCoverTest extends TestCase class PlaylistCoverTest extends TestCase
{ {
public function testUploadCover(): void #[Test]
public function uploadCover(): void
{ {
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
self::assertNull($playlist->cover); self::assertNull($playlist->cover);
@ -26,7 +28,8 @@ class PlaylistCoverTest extends TestCase
self::assertNotNull($playlist->refresh()->cover); self::assertNotNull($playlist->refresh()->cover);
} }
public function testUploadCoverNotAllowedForNonOwner(): void #[Test]
public function uploadCoverNotAllowedForNonOwner(): void
{ {
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -34,7 +37,8 @@ class PlaylistCoverTest extends TestCase
->assertForbidden(); ->assertForbidden();
} }
public function testDeleteCover(): void #[Test]
public function deleteCover(): void
{ {
$playlist = Playlist::factory()->create(['cover' => 'cover.jpg']); $playlist = Playlist::factory()->create(['cover' => 'cover.jpg']);
@ -44,7 +48,8 @@ class PlaylistCoverTest extends TestCase
self::assertNull($playlist->refresh()->cover); self::assertNull($playlist->refresh()->cover);
} }
public function testNonOwnerCannotDeleteCover(): void #[Test]
public function nonOwnerCannotDeleteCover(): void
{ {
$playlist = Playlist::factory()->create(['cover' => 'cover.jpg']); $playlist = Playlist::factory()->create(['cover' => 'cover.jpg']);

View file

@ -5,13 +5,15 @@ namespace Tests\Feature;
use App\Http\Resources\PlaylistFolderResource; use App\Http\Resources\PlaylistFolderResource;
use App\Models\Playlist; use App\Models\Playlist;
use App\Models\PlaylistFolder; use App\Models\PlaylistFolder;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class PlaylistFolderTest extends TestCase class PlaylistFolderTest extends TestCase
{ {
public function testListing(): void #[Test]
public function listing(): void
{ {
$user = create_user(); $user = create_user();
PlaylistFolder::factory()->for($user)->count(3)->create(); PlaylistFolder::factory()->for($user)->count(3)->create();
@ -21,7 +23,8 @@ class PlaylistFolderTest extends TestCase
->assertJsonCount(3, '*'); ->assertJsonCount(3, '*');
} }
public function testCreate(): void #[Test]
public function create(): void
{ {
$user = create_user(); $user = create_user();
@ -31,7 +34,8 @@ class PlaylistFolderTest extends TestCase
$this->assertDatabaseHas(PlaylistFolder::class, ['name' => 'Classical', 'user_id' => $user->id]); $this->assertDatabaseHas(PlaylistFolder::class, ['name' => 'Classical', 'user_id' => $user->id]);
} }
public function testUpdate(): void #[Test]
public function update(): void
{ {
$folder = PlaylistFolder::factory()->create(['name' => 'Metal']); $folder = PlaylistFolder::factory()->create(['name' => 'Metal']);
@ -41,7 +45,8 @@ class PlaylistFolderTest extends TestCase
self::assertSame('Classical', $folder->fresh()->name); self::assertSame('Classical', $folder->fresh()->name);
} }
public function testUnauthorizedUpdate(): void #[Test]
public function unauthorizedUpdate(): void
{ {
$folder = PlaylistFolder::factory()->create(['name' => 'Metal']); $folder = PlaylistFolder::factory()->create(['name' => 'Metal']);
@ -51,7 +56,8 @@ class PlaylistFolderTest extends TestCase
self::assertSame('Metal', $folder->fresh()->name); self::assertSame('Metal', $folder->fresh()->name);
} }
public function testDelete(): void #[Test]
public function destroy(): void
{ {
$folder = PlaylistFolder::factory()->create(); $folder = PlaylistFolder::factory()->create();
@ -61,7 +67,8 @@ class PlaylistFolderTest extends TestCase
self::assertModelMissing($folder); self::assertModelMissing($folder);
} }
public function testNonAuthorizedDelete(): void #[Test]
public function nonAuthorizedDelete(): void
{ {
/** @var PlaylistFolder $folder */ /** @var PlaylistFolder $folder */
$folder = PlaylistFolder::factory()->create(); $folder = PlaylistFolder::factory()->create();
@ -72,7 +79,8 @@ class PlaylistFolderTest extends TestCase
self::assertModelExists($folder); self::assertModelExists($folder);
} }
public function testMovingPlaylistToFolder(): void #[Test]
public function movingPlaylistToFolder(): void
{ {
/** @var PlaylistFolder $folder */ /** @var PlaylistFolder $folder */
$folder = PlaylistFolder::factory()->create(); $folder = PlaylistFolder::factory()->create();
@ -87,7 +95,8 @@ class PlaylistFolderTest extends TestCase
self::assertTrue($playlist->fresh()->getFolder($folder->user)->is($folder)); self::assertTrue($playlist->fresh()->getFolder($folder->user)->is($folder));
} }
public function testUnauthorizedMovingPlaylistToFolderIsNotAllowed(): void #[Test]
public function unauthorizedMovingPlaylistToFolderIsNotAllowed(): void
{ {
/** @var PlaylistFolder $folder */ /** @var PlaylistFolder $folder */
$folder = PlaylistFolder::factory()->create(); $folder = PlaylistFolder::factory()->create();
@ -102,7 +111,8 @@ class PlaylistFolderTest extends TestCase
self::assertNull($playlist->fresh()->getFolder($folder->user)); self::assertNull($playlist->fresh()->getFolder($folder->user));
} }
public function testMovingPlaylistToRootLevel(): void #[Test]
public function movingPlaylistToRootLevel(): void
{ {
/** @var PlaylistFolder $folder */ /** @var PlaylistFolder $folder */
$folder = PlaylistFolder::factory()->create(); $folder = PlaylistFolder::factory()->create();
@ -119,7 +129,8 @@ class PlaylistFolderTest extends TestCase
self::assertNull($playlist->fresh()->getFolder($folder->user)); self::assertNull($playlist->fresh()->getFolder($folder->user));
} }
public function testUnauthorizedMovingPlaylistToRootLevelIsNotAllowed(): void #[Test]
public function unauthorizedMovingPlaylistToRootLevelIsNotAllowed(): void
{ {
/** @var PlaylistFolder $folder */ /** @var PlaylistFolder $folder */
$folder = PlaylistFolder::factory()->create(); $folder = PlaylistFolder::factory()->create();

View file

@ -6,13 +6,15 @@ use App\Http\Resources\SongResource;
use App\Models\Playlist; use App\Models\Playlist;
use App\Models\Song; use App\Models\Song;
use Illuminate\Support\Collection; use Illuminate\Support\Collection;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class PlaylistSongTest extends TestCase class PlaylistSongTest extends TestCase
{ {
public function testGetNormalPlaylist(): void #[Test]
public function getNormalPlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -22,7 +24,8 @@ class PlaylistSongTest extends TestCase
->assertJsonStructure(['*' => SongResource::JSON_STRUCTURE]); ->assertJsonStructure(['*' => SongResource::JSON_STRUCTURE]);
} }
public function testGetSmartPlaylist(): void #[Test]
public function getSmartPlaylist(): void
{ {
Song::factory()->create(['title' => 'A foo song']); Song::factory()->create(['title' => 'A foo song']);
@ -47,7 +50,8 @@ class PlaylistSongTest extends TestCase
->assertJsonStructure(['*' => SongResource::JSON_STRUCTURE]); ->assertJsonStructure(['*' => SongResource::JSON_STRUCTURE]);
} }
public function testNonOwnerCannotAccessPlaylist(): void #[Test]
public function nonOwnerCannotAccessPlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->for(create_user())->create(); $playlist = Playlist::factory()->for(create_user())->create();
@ -57,7 +61,8 @@ class PlaylistSongTest extends TestCase
->assertForbidden(); ->assertForbidden();
} }
public function testAddSongsToPlaylist(): void #[Test]
public function addSongsToPlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -71,7 +76,8 @@ class PlaylistSongTest extends TestCase
self::assertEqualsCanonicalizing($songs->pluck('id')->all(), $playlist->playables->pluck('id')->all()); self::assertEqualsCanonicalizing($songs->pluck('id')->all(), $playlist->playables->pluck('id')->all());
} }
public function testRemoveSongsFromPlaylist(): void #[Test]
public function removeSongsFromPlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -97,7 +103,8 @@ class PlaylistSongTest extends TestCase
self::assertEqualsCanonicalizing($toRemainSongs->pluck('id')->all(), $playlist->playables->pluck('id')->all()); self::assertEqualsCanonicalizing($toRemainSongs->pluck('id')->all(), $playlist->playables->pluck('id')->all());
} }
public function testNonOwnerCannotModifyPlaylist(): void #[Test]
public function nonOwnerCannotModifyPlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->for(create_user())->create(); $playlist = Playlist::factory()->for(create_user())->create();
@ -112,7 +119,8 @@ class PlaylistSongTest extends TestCase
->assertForbidden(); ->assertForbidden();
} }
public function testSmartPlaylistContentCannotBeModified(): void #[Test]
public function smartPlaylistContentCannotBeModified(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create([ $playlist = Playlist::factory()->create([

View file

@ -7,13 +7,15 @@ use App\Models\Playlist;
use App\Models\Song; use App\Models\Song;
use App\Values\SmartPlaylistRule; use App\Values\SmartPlaylistRule;
use Illuminate\Support\Collection; use Illuminate\Support\Collection;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class PlaylistTest extends TestCase class PlaylistTest extends TestCase
{ {
public function testListing(): void #[Test]
public function listing(): void
{ {
$user = create_user(); $user = create_user();
Playlist::factory()->for($user)->count(3)->create(); Playlist::factory()->for($user)->count(3)->create();
@ -23,7 +25,8 @@ class PlaylistTest extends TestCase
->assertJsonCount(3, '*'); ->assertJsonCount(3, '*');
} }
public function testCreatingPlaylist(): void #[Test]
public function creatingPlaylist(): void
{ {
$user = create_user(); $user = create_user();
@ -46,7 +49,8 @@ class PlaylistTest extends TestCase
self::assertEqualsCanonicalizing($songs->pluck('id')->all(), $playlist->playables->pluck('id')->all()); self::assertEqualsCanonicalizing($songs->pluck('id')->all(), $playlist->playables->pluck('id')->all());
} }
public function testCreatingSmartPlaylist(): void #[Test]
public function creatingSmartPlaylist(): void
{ {
$user = create_user(); $user = create_user();
@ -77,7 +81,8 @@ class PlaylistTest extends TestCase
self::assertTrue($rule->equals($playlist->rule_groups[0]->rules[0])); self::assertTrue($rule->equals($playlist->rule_groups[0]->rules[0]));
} }
public function testCreatingSmartPlaylistFailsIfSongsProvided(): void #[Test]
public function creatingSmartPlaylistFailsIfSongsProvided(): void
{ {
$this->postAs('api/playlists', [ $this->postAs('api/playlists', [
'name' => 'Smart Foo Bar', 'name' => 'Smart Foo Bar',
@ -97,7 +102,8 @@ class PlaylistTest extends TestCase
])->assertUnprocessable(); ])->assertUnprocessable();
} }
public function testCreatingPlaylistWithNonExistentSongsFails(): void #[Test]
public function creatingPlaylistWithNonExistentSongsFails(): void
{ {
$this->postAs('api/playlists', [ $this->postAs('api/playlists', [
'name' => 'Foo Bar', 'name' => 'Foo Bar',
@ -107,7 +113,8 @@ class PlaylistTest extends TestCase
->assertUnprocessable(); ->assertUnprocessable();
} }
public function testUpdatePlaylistName(): void #[Test]
public function updatePlaylistName(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(['name' => 'Foo']); $playlist = Playlist::factory()->create(['name' => 'Foo']);
@ -118,7 +125,8 @@ class PlaylistTest extends TestCase
self::assertSame('Bar', $playlist->refresh()->name); self::assertSame('Bar', $playlist->refresh()->name);
} }
public function testNonOwnerCannotUpdatePlaylist(): void #[Test]
public function nonOwnerCannotUpdatePlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(['name' => 'Foo']); $playlist = Playlist::factory()->create(['name' => 'Foo']);
@ -127,7 +135,8 @@ class PlaylistTest extends TestCase
self::assertSame('Foo', $playlist->refresh()->name); self::assertSame('Foo', $playlist->refresh()->name);
} }
public function testDeletePlaylist(): void #[Test]
public function deletePlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -137,7 +146,8 @@ class PlaylistTest extends TestCase
self::assertModelMissing($playlist); self::assertModelMissing($playlist);
} }
public function testNonOwnerCannotDeletePlaylist(): void #[Test]
public function nonOwnerCannotDeletePlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();

View file

@ -3,6 +3,7 @@
namespace Tests\Feature; namespace Tests\Feature;
use Illuminate\Support\Facades\Hash; use Illuminate\Support\Facades\Hash;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
@ -11,7 +12,8 @@ use function Tests\test_path;
class ProfileTest extends TestCase class ProfileTest extends TestCase
{ {
public function testUpdateProfileRequiresCurrentPassword(): void #[Test]
public function updateProfileRequiresCurrentPassword(): void
{ {
$this->putAs('api/me', [ $this->putAs('api/me', [
'name' => 'Foo', 'name' => 'Foo',
@ -20,7 +22,8 @@ class ProfileTest extends TestCase
->assertUnprocessable(); ->assertUnprocessable();
} }
public function testUpdateProfileWithoutNewPassword(): void #[Test]
public function updateProfileWithoutNewPassword(): void
{ {
$user = create_user(['password' => Hash::make('secret')]); $user = create_user(['password' => Hash::make('secret')]);
@ -37,7 +40,8 @@ class ProfileTest extends TestCase
self::assertTrue(Hash::check('secret', $user->password)); self::assertTrue(Hash::check('secret', $user->password));
} }
public function testUpdateProfileWithNewPassword(): void #[Test]
public function updateProfileWithNewPassword(): void
{ {
$user = create_user(['password' => Hash::make('secret')]); $user = create_user(['password' => Hash::make('secret')]);
@ -58,7 +62,8 @@ class ProfileTest extends TestCase
self::assertTrue(Hash::check('new-secret', $user->password)); self::assertTrue(Hash::check('new-secret', $user->password));
} }
public function testUpdateProfileWithAvatar(): void #[Test]
public function updateProfileWithAvatar(): void
{ {
$user = create_user(['password' => Hash::make('secret')]); $user = create_user(['password' => Hash::make('secret')]);
self::assertNull($user->getRawOriginal('avatar')); self::assertNull($user->getRawOriginal('avatar'));
@ -76,7 +81,8 @@ class ProfileTest extends TestCase
self::assertFileExists(user_avatar_path($user->getRawOriginal('avatar'))); self::assertFileExists(user_avatar_path($user->getRawOriginal('avatar')));
} }
public function testUpdateProfileRemovingAvatar(): void #[Test]
public function updateProfileRemovingAvatar(): void
{ {
$user = create_user([ $user = create_user([
'password' => Hash::make('secret'), 'password' => Hash::make('secret'),

View file

@ -5,6 +5,7 @@ namespace Tests\Feature;
use App\Http\Resources\SongResource; use App\Http\Resources\SongResource;
use App\Models\QueueState; use App\Models\QueueState;
use App\Models\Song; use App\Models\Song;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
@ -17,13 +18,15 @@ class QueueTest extends TestCase
'playback_position', 'playback_position',
]; ];
public function testGetEmptyState(): void #[Test]
public function getEmptyState(): void
{ {
$this->getAs('api/queue/state') $this->getAs('api/queue/state')
->assertJsonStructure(self::QUEUE_STATE_JSON_STRUCTURE); ->assertJsonStructure(self::QUEUE_STATE_JSON_STRUCTURE);
} }
public function testGetExistingState(): void #[Test]
public function getExistingState(): void
{ {
/** @var QueueState $queueState */ /** @var QueueState $queueState */
$queueState = QueueState::factory()->create([ $queueState = QueueState::factory()->create([
@ -35,7 +38,8 @@ class QueueTest extends TestCase
->assertJsonStructure(self::QUEUE_STATE_JSON_STRUCTURE); ->assertJsonStructure(self::QUEUE_STATE_JSON_STRUCTURE);
} }
public function testUpdateStateWithoutExistingState(): void #[Test]
public function updateStateWithoutExistingState(): void
{ {
$user = create_user(); $user = create_user();
@ -51,7 +55,8 @@ class QueueTest extends TestCase
self::assertEqualsCanonicalizing($songIds, $queue->song_ids); self::assertEqualsCanonicalizing($songIds, $queue->song_ids);
} }
public function testUpdatePlaybackStatus(): void #[Test]
public function updatePlaybackStatus(): void
{ {
/** @var QueueState $state */ /** @var QueueState $state */
$state = QueueState::factory()->create(); $state = QueueState::factory()->create();
@ -77,7 +82,8 @@ class QueueTest extends TestCase
self::assertSame(456, $state->playback_position); self::assertSame(456, $state->playback_position);
} }
public function testFetchSongs(): void #[Test]
public function fetchSongs(): void
{ {
Song::factory(10)->create(); Song::factory(10)->create();

View file

@ -4,13 +4,15 @@ namespace Tests\Feature;
use App\Http\Resources\SongResource; use App\Http\Resources\SongResource;
use App\Models\Interaction; use App\Models\Interaction;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class RecentlyPlayedSongTest extends TestCase class RecentlyPlayedSongTest extends TestCase
{ {
public function testIndex(): void #[Test]
public function index(): void
{ {
$user = create_user(); $user = create_user();

View file

@ -6,13 +6,15 @@ use App\Models\Song;
use App\Models\User; use App\Models\User;
use App\Services\LastfmService; use App\Services\LastfmService;
use Mockery; use Mockery;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class ScrobbleTest extends TestCase class ScrobbleTest extends TestCase
{ {
public function testLastfmScrobble(): void #[Test]
public function lastfmScrobble(): void
{ {
$user = create_user(); $user = create_user();

View file

@ -6,6 +6,7 @@ use App\Models\Setting;
use App\Services\MediaScanner; use App\Services\MediaScanner;
use App\Values\ScanResultCollection; use App\Values\ScanResultCollection;
use Mockery\MockInterface; use Mockery\MockInterface;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
@ -21,7 +22,8 @@ class SettingTest extends TestCase
$this->mediaScanner = self::mock(MediaScanner::class); $this->mediaScanner = self::mock(MediaScanner::class);
} }
public function testSaveSettings(): void #[Test]
public function saveSettings(): void
{ {
$this->mediaScanner->shouldReceive('scan')->once() $this->mediaScanner->shouldReceive('scan')->once()
->andReturn(ScanResultCollection::create()); ->andReturn(ScanResultCollection::create());
@ -32,13 +34,15 @@ class SettingTest extends TestCase
self::assertSame(__DIR__, Setting::get('media_path')); self::assertSame(__DIR__, Setting::get('media_path'));
} }
public function testNonAdminCannotSaveSettings(): void #[Test]
public function nonAdminCannotSaveSettings(): void
{ {
$this->putAs('/api/settings', ['media_path' => __DIR__]) $this->putAs('/api/settings', ['media_path' => __DIR__])
->assertForbidden(); ->assertForbidden();
} }
public function testMediaPathCannotBeSetForCloudStorage(): void #[Test]
public function mediaPathCannotBeSetForCloudStorage(): void
{ {
config(['koel.storage_driver' => 's3']); config(['koel.storage_driver' => 's3']);

View file

@ -8,6 +8,7 @@ use App\Services\Streamer\Adapters\TranscodingStreamerAdapter;
use App\Services\TokenManager; use App\Services\TokenManager;
use App\Values\CompositeToken; use App\Values\CompositeToken;
use Illuminate\Support\Facades\File; use Illuminate\Support\Facades\File;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
@ -15,7 +16,8 @@ use function Tests\test_path;
class SongPlayTest extends TestCase class SongPlayTest extends TestCase
{ {
public function testPlay(): void #[Test]
public function play(): void
{ {
$user = create_user(); $user = create_user();
@ -35,7 +37,8 @@ class SongPlayTest extends TestCase
->assertOk(); ->assertOk();
} }
public function testTranscoding(): void #[Test]
public function transcoding(): void
{ {
config(['koel.streaming.transcode_flac' => true]); config(['koel.streaming.transcode_flac' => true]);
$user = create_user(); $user = create_user();
@ -61,7 +64,8 @@ class SongPlayTest extends TestCase
config(['koel.streaming.transcode_flac' => false]); config(['koel.streaming.transcode_flac' => false]);
} }
public function testForceTranscoding(): void #[Test]
public function forceTranscoding(): void
{ {
$user = create_user(); $user = create_user();

View file

@ -4,11 +4,13 @@ namespace Tests\Feature;
use App\Http\Resources\SongResource; use App\Http\Resources\SongResource;
use App\Models\Song; use App\Models\Song;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class SongSearchTest extends TestCase class SongSearchTest extends TestCase
{ {
public function testSearch(): void #[Test]
public function search(): void
{ {
Song::factory(10)->create(['title' => 'A Foo Song']); Song::factory(10)->create(['title' => 'A Foo Song']);

View file

@ -7,13 +7,15 @@ use App\Models\Album;
use App\Models\Artist; use App\Models\Artist;
use App\Models\Song; use App\Models\Song;
use Illuminate\Support\Collection; use Illuminate\Support\Collection;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
class SongTest extends TestCase class SongTest extends TestCase
{ {
public function testIndex(): void #[Test]
public function index(): void
{ {
Song::factory(10)->create(); Song::factory(10)->create();
@ -21,7 +23,8 @@ class SongTest extends TestCase
$this->getAs('api/songs?sort=title&order=desc')->assertJsonStructure(SongResource::PAGINATION_JSON_STRUCTURE); $this->getAs('api/songs?sort=title&order=desc')->assertJsonStructure(SongResource::PAGINATION_JSON_STRUCTURE);
} }
public function testShow(): void #[Test]
public function show(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->create(); $song = Song::factory()->create();
@ -29,7 +32,8 @@ class SongTest extends TestCase
$this->getAs('api/songs/' . $song->id)->assertJsonStructure(SongResource::JSON_STRUCTURE); $this->getAs('api/songs/' . $song->id)->assertJsonStructure(SongResource::JSON_STRUCTURE);
} }
public function testDelete(): void #[Test]
public function destroy(): void
{ {
/** @var Collection<array-key, Song> $songs */ /** @var Collection<array-key, Song> $songs */
$songs = Song::factory(3)->create(); $songs = Song::factory(3)->create();
@ -40,7 +44,8 @@ class SongTest extends TestCase
$songs->each(fn (Song $song) => $this->assertModelMissing($song)); $songs->each(fn (Song $song) => $this->assertModelMissing($song));
} }
public function testUnauthorizedDelete(): void #[Test]
public function unauthorizedDelete(): void
{ {
/** @var Collection<array-key, Song> $songs */ /** @var Collection<array-key, Song> $songs */
$songs = Song::factory(3)->create(); $songs = Song::factory(3)->create();
@ -51,7 +56,8 @@ class SongTest extends TestCase
$songs->each(fn (Song $song) => $this->assertModelExists($song)); $songs->each(fn (Song $song) => $this->assertModelExists($song));
} }
public function testSingleUpdateAllInfoNoCompilation(): void #[Test]
public function singleUpdateAllInfoNoCompilation(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->create(); $song = Song::factory()->create();
@ -86,7 +92,8 @@ class SongTest extends TestCase
]); ]);
} }
public function testSingleUpdateSomeInfoNoCompilation(): void #[Test]
public function singleUpdateSomeInfoNoCompilation(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->create(); $song = Song::factory()->create();
@ -112,7 +119,8 @@ class SongTest extends TestCase
self::assertSame('One by One', $song->album->name); self::assertSame('One by One', $song->album->name);
} }
public function testMultipleUpdateNoCompilation(): void #[Test]
public function multipleUpdateNoCompilation(): void
{ {
$songIds = Song::factory(3)->create()->pluck('id')->all(); $songIds = Song::factory(3)->create()->pluck('id')->all();
@ -148,7 +156,8 @@ class SongTest extends TestCase
self::assertSame(9999, $songs[2]->track); self::assertSame(9999, $songs[2]->track);
} }
public function testMultipleUpdateCreatingNewAlbumsAndArtists(): void #[Test]
public function multipleUpdateCreatingNewAlbumsAndArtists(): void
{ {
/** @var Collection<array-key, Song> $originalSongs */ /** @var Collection<array-key, Song> $originalSongs */
$originalSongs = Song::factory(3)->create(); $originalSongs = Song::factory(3)->create();
@ -184,7 +193,8 @@ class SongTest extends TestCase
self::assertSame('John Cena', $songs[2]->artist->name); // And... JOHN CENAAAAAAAAAAA!!! self::assertSame('John Cena', $songs[2]->artist->name); // And... JOHN CENAAAAAAAAAAA!!!
} }
public function testSingleUpdateAllInfoWithCompilation(): void #[Test]
public function singleUpdateAllInfoWithCompilation(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->create(); $song = Song::factory()->create();
@ -224,7 +234,8 @@ class SongTest extends TestCase
self::assertTrue($album->artist->is($albumArtist)); self::assertTrue($album->artist->is($albumArtist));
} }
public function testUpdateSingleSongWithEmptyTrackAndDisc(): void #[Test]
public function updateSingleSongWithEmptyTrackAndDisc(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->create([ $song = Song::factory()->create([
@ -247,7 +258,8 @@ class SongTest extends TestCase
self::assertSame(1, $song->disc); self::assertSame(1, $song->disc);
} }
public function testDeletingByChunk(): void #[Test]
public function deletingByChunk(): void
{ {
Song::factory(5)->create(); Song::factory(5)->create();

View file

@ -3,13 +3,15 @@
namespace Tests\Feature; namespace Tests\Feature;
use App\Models\Song; use App\Models\Song;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
class SongVisibilityTest extends TestCase class SongVisibilityTest extends TestCase
{ {
public function testChangingVisibilityIsForbiddenInCommunityEdition(): void #[Test]
public function changingVisibilityIsForbiddenInCommunityEdition(): void
{ {
$owner = create_admin(); $owner = create_admin();
Song::factory(3)->create(); Song::factory(3)->create();

View file

@ -7,6 +7,7 @@ use App\Exceptions\SongUploadFailedException;
use App\Models\Setting; use App\Models\Setting;
use Illuminate\Http\Response; use Illuminate\Http\Response;
use Illuminate\Http\UploadedFile; use Illuminate\Http\UploadedFile;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
@ -23,7 +24,8 @@ class UploadTest extends TestCase
$this->file = UploadedFile::fromFile(test_path('songs/full.mp3'), 'song.mp3'); //@phpstan-ignore-line $this->file = UploadedFile::fromFile(test_path('songs/full.mp3'), 'song.mp3'); //@phpstan-ignore-line
} }
public function testUnauthorizedPost(): void #[Test]
public function unauthorizedPost(): void
{ {
Setting::set('media_path', ''); Setting::set('media_path', '');
@ -39,14 +41,16 @@ class UploadTest extends TestCase
]; ];
} }
public function testUploadFailsIfMediaPathIsNotSet(): void #[Test]
public function uploadFailsIfMediaPathIsNotSet(): void
{ {
Setting::set('media_path', ''); Setting::set('media_path', '');
$this->postAs('/api/upload', ['file' => $this->file], create_admin())->assertForbidden(); $this->postAs('/api/upload', ['file' => $this->file], create_admin())->assertForbidden();
} }
public function testUploadSuccessful(): void #[Test]
public function uploadSuccessful(): void
{ {
Setting::set('media_path', public_path('sandbox/media')); Setting::set('media_path', public_path('sandbox/media'));

View file

@ -7,13 +7,15 @@ use App\Mail\UserInvite;
use App\Models\User; use App\Models\User;
use Illuminate\Support\Facades\Mail; use Illuminate\Support\Facades\Mail;
use Illuminate\Support\Str; use Illuminate\Support\Str;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
class UserInvitationTest extends TestCase class UserInvitationTest extends TestCase
{ {
public function testInvite(): void #[Test]
public function invite(): void
{ {
Mail::fake(); Mail::fake();
@ -27,7 +29,8 @@ class UserInvitationTest extends TestCase
Mail::assertQueued(UserInvite::class, 2); Mail::assertQueued(UserInvite::class, 2);
} }
public function testNonAdminCannotInvite(): void #[Test]
public function nonAdminCannotInvite(): void
{ {
Mail::fake(); Mail::fake();
@ -37,7 +40,8 @@ class UserInvitationTest extends TestCase
Mail::assertNothingQueued(); Mail::assertNothingQueued();
} }
public function testGetProspect(): void #[Test]
public function getProspect(): void
{ {
$prospect = self::createProspect(); $prospect = self::createProspect();
@ -46,7 +50,8 @@ class UserInvitationTest extends TestCase
->assertJsonStructure(UserProspectResource::JSON_STRUCTURE); ->assertJsonStructure(UserProspectResource::JSON_STRUCTURE);
} }
public function testRevoke(): void #[Test]
public function revoke(): void
{ {
$prospect = self::createProspect(); $prospect = self::createProspect();
@ -56,7 +61,8 @@ class UserInvitationTest extends TestCase
self::assertModelMissing($prospect); self::assertModelMissing($prospect);
} }
public function testNonAdminCannotRevoke(): void #[Test]
public function nonAdminCannotRevoke(): void
{ {
$prospect = self::createProspect(); $prospect = self::createProspect();
@ -66,7 +72,8 @@ class UserInvitationTest extends TestCase
self::assertModelExists($prospect); self::assertModelExists($prospect);
} }
public function testAccept(): void #[Test]
public function accept(): void
{ {
$prospect = self::createProspect(); $prospect = self::createProspect();

View file

@ -4,6 +4,7 @@ namespace Tests\Feature;
use App\Models\User; use App\Models\User;
use Illuminate\Support\Facades\Hash; use Illuminate\Support\Facades\Hash;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
@ -11,7 +12,8 @@ use function Tests\create_user;
class UserTest extends TestCase class UserTest extends TestCase
{ {
public function testNonAdminCannotCreateUser(): void #[Test]
public function nonAdminCannotCreateUser(): void
{ {
$this->postAs('api/user', [ $this->postAs('api/user', [
'name' => 'Foo', 'name' => 'Foo',
@ -21,7 +23,8 @@ class UserTest extends TestCase
])->assertForbidden(); ])->assertForbidden();
} }
public function testAdminCreatesUser(): void #[Test]
public function adminCreatesUser(): void
{ {
$admin = create_admin(); $admin = create_admin();
@ -42,7 +45,8 @@ class UserTest extends TestCase
self::assertTrue($user->is_admin); self::assertTrue($user->is_admin);
} }
public function testAdminUpdatesUser(): void #[Test]
public function adminUpdatesUser(): void
{ {
$admin = create_admin(); $admin = create_admin();
$user = create_admin(['password' => 'secret']); $user = create_admin(['password' => 'secret']);
@ -63,7 +67,8 @@ class UserTest extends TestCase
self::assertFalse($user->is_admin); self::assertFalse($user->is_admin);
} }
public function testAdminDeletesUser(): void #[Test]
public function adminDeletesUser(): void
{ {
$user = create_user(); $user = create_user();
@ -71,7 +76,8 @@ class UserTest extends TestCase
self::assertModelMissing($user); self::assertModelMissing($user);
} }
public function testSelfDeletionNotAllowed(): void #[Test]
public function selfDeletionNotAllowed(): void
{ {
$admin = create_admin(); $admin = create_admin();

View file

@ -6,6 +6,7 @@ use App\Models\Song;
use App\Services\YouTubeService; use App\Services\YouTubeService;
use Mockery; use Mockery;
use Mockery\MockInterface; use Mockery\MockInterface;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class YouTubeTest extends TestCase class YouTubeTest extends TestCase
@ -19,7 +20,8 @@ class YouTubeTest extends TestCase
$this->youTubeService = self::mock(YouTubeService::class); $this->youTubeService = self::mock(YouTubeService::class);
} }
public function testSearchYouTubeVideos(): void #[Test]
public function searchYouTubeVideos(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->create(); $song = Song::factory()->create();

View file

@ -3,13 +3,15 @@
namespace Tests\Integration\Casts; namespace Tests\Integration\Casts;
use App\Values\UserPreferences; use App\Values\UserPreferences;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class UserPreferencesCastTest extends TestCase class UserPreferencesCastTest extends TestCase
{ {
public function testCast(): void #[Test]
public function cast(): void
{ {
$user = create_user([ $user = create_user([
'preferences' => [ 'preferences' => [

View file

@ -3,11 +3,13 @@
namespace Tests\Integration\Enums; namespace Tests\Integration\Enums;
use App\Enums\SongStorageType; use App\Enums\SongStorageType;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class SongStorageTypeTest extends TestCase class SongStorageTypeTest extends TestCase
{ {
public function testSupported(): void #[Test]
public function supported(): void
{ {
self::assertTrue(SongStorageType::LOCAL->supported()); self::assertTrue(SongStorageType::LOCAL->supported());
self::assertTrue(SongStorageType::S3_LAMBDA->supported()); self::assertTrue(SongStorageType::S3_LAMBDA->supported());

View file

@ -3,11 +3,13 @@
namespace Tests\Integration\KoelPlus\Enums; namespace Tests\Integration\KoelPlus\Enums;
use App\Enums\SongStorageType; use App\Enums\SongStorageType;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
class SongStorageTypeTest extends PlusTestCase class SongStorageTypeTest extends PlusTestCase
{ {
public function testSupported(): void #[Test]
public function supported(): void
{ {
self::assertTrue(collect(SongStorageType::cases())->every( self::assertTrue(collect(SongStorageType::cases())->every(
static fn (SongStorageType $type) => $type->supported() static fn (SongStorageType $type) => $type->supported()

View file

@ -11,6 +11,7 @@ use App\Models\Playlist;
use App\Models\PlaylistCollaborationToken; use App\Models\PlaylistCollaborationToken;
use App\Services\PlaylistCollaborationService; use App\Services\PlaylistCollaborationService;
use Illuminate\Support\Facades\Event; use Illuminate\Support\Facades\Event;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
@ -26,7 +27,8 @@ class PlaylistCollaborationServiceTest extends PlusTestCase
$this->service = app(PlaylistCollaborationService::class); $this->service = app(PlaylistCollaborationService::class);
} }
public function testCreateToken(): void #[Test]
public function createToken(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -38,7 +40,8 @@ class PlaylistCollaborationServiceTest extends PlusTestCase
self::assertSame($playlist->id, $token->playlist_id); self::assertSame($playlist->id, $token->playlist_id);
} }
public function testCreateTokenFailsIfPlaylistIsSmart(): void #[Test]
public function createTokenFailsIfPlaylistIsSmart(): void
{ {
$this->expectException(OperationNotApplicableForSmartPlaylistException::class); $this->expectException(OperationNotApplicableForSmartPlaylistException::class);
@ -48,7 +51,8 @@ class PlaylistCollaborationServiceTest extends PlusTestCase
$this->service->createToken($playlist); $this->service->createToken($playlist);
} }
public function testAcceptUsingToken(): void #[Test]
public function acceptUsingToken(): void
{ {
Event::fake(NewPlaylistCollaboratorJoined::class); Event::fake(NewPlaylistCollaboratorJoined::class);
@ -63,7 +67,8 @@ class PlaylistCollaborationServiceTest extends PlusTestCase
Event::assertDispatched(NewPlaylistCollaboratorJoined::class); Event::assertDispatched(NewPlaylistCollaboratorJoined::class);
} }
public function testFailsToAcceptExpiredToken(): void #[Test]
public function failsToAcceptExpiredToken(): void
{ {
$this->expectException(PlaylistCollaborationTokenExpiredException::class); $this->expectException(PlaylistCollaborationTokenExpiredException::class);
Event::fake(NewPlaylistCollaboratorJoined::class); Event::fake(NewPlaylistCollaboratorJoined::class);
@ -80,7 +85,8 @@ class PlaylistCollaborationServiceTest extends PlusTestCase
Event::assertNotDispatched(NewPlaylistCollaboratorJoined::class); Event::assertNotDispatched(NewPlaylistCollaboratorJoined::class);
} }
public function testGetCollaborators(): void #[Test]
public function getCollaborators(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -92,7 +98,8 @@ class PlaylistCollaborationServiceTest extends PlusTestCase
self::assertEqualsCanonicalizing([$playlist->user_id, $user->id], $collaborators->pluck('id')->toArray()); self::assertEqualsCanonicalizing([$playlist->user_id, $user->id], $collaborators->pluck('id')->toArray());
} }
public function testRemoveCollaborator(): void #[Test]
public function removeCollaborator(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -106,7 +113,8 @@ class PlaylistCollaborationServiceTest extends PlusTestCase
self::assertFalse($playlist->refresh()->hasCollaborator($user)); self::assertFalse($playlist->refresh()->hasCollaborator($user));
} }
public function testCannotRemoveNonExistingCollaborator(): void #[Test]
public function cannotRemoveNonExistingCollaborator(): void
{ {
$this->expectException(NotAPlaylistCollaboratorException::class); $this->expectException(NotAPlaylistCollaboratorException::class);
@ -117,7 +125,8 @@ class PlaylistCollaborationServiceTest extends PlusTestCase
$this->service->removeCollaborator($playlist, $user); $this->service->removeCollaborator($playlist, $user);
} }
public function testCannotRemoveOwner(): void #[Test]
public function cannotRemoveOwner(): void
{ {
$this->expectException(CannotRemoveOwnerFromPlaylistException::class); $this->expectException(CannotRemoveOwnerFromPlaylistException::class);

View file

@ -6,6 +6,7 @@ use App\Models\Playlist;
use App\Services\PlaylistService; use App\Services\PlaylistService;
use App\Values\SmartPlaylistRuleGroupCollection; use App\Values\SmartPlaylistRuleGroupCollection;
use InvalidArgumentException; use InvalidArgumentException;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
@ -21,7 +22,8 @@ class PlaylistServiceTest extends PlusTestCase
$this->service = app(PlaylistService::class); $this->service = app(PlaylistService::class);
} }
public function testCreatePlaylistWithOwnSongsOnlyOption(): void #[Test]
public function createPlaylistWithOwnSongsOnlyOption(): void
{ {
$rules = SmartPlaylistRuleGroupCollection::create([ $rules = SmartPlaylistRuleGroupCollection::create([
[ [
@ -51,7 +53,8 @@ class PlaylistServiceTest extends PlusTestCase
self::assertTrue($playlist->own_songs_only); self::assertTrue($playlist->own_songs_only);
} }
public function testOwnSongsOnlyOptionOnlyWorksWithSmartPlaylistsWhenCreate(): void #[Test]
public function ownSongsOnlyOptionOnlyWorksWithSmartPlaylistsWhenCreate(): void
{ {
$this->expectException(InvalidArgumentException::class); $this->expectException(InvalidArgumentException::class);
$this->expectExceptionMessage('"Own songs only" option only works with smart playlists and Plus license.'); $this->expectExceptionMessage('"Own songs only" option only works with smart playlists and Plus license.');
@ -63,7 +66,8 @@ class PlaylistServiceTest extends PlusTestCase
); );
} }
public function testOwnSongsOnlyOptionOnlyWorksWithSmartPlaylistsWhenUpdate(): void #[Test]
public function ownSongsOnlyOptionOnlyWorksWithSmartPlaylistsWhenUpdate(): void
{ {
$this->expectException(InvalidArgumentException::class); $this->expectException(InvalidArgumentException::class);
$this->expectExceptionMessage('"Own songs only" option only works with smart playlists and Plus license.'); $this->expectExceptionMessage('"Own songs only" option only works with smart playlists and Plus license.');

View file

@ -6,6 +6,7 @@ use App\Models\Playlist;
use App\Models\Song; use App\Models\Song;
use App\Services\SmartPlaylistService; use App\Services\SmartPlaylistService;
use Illuminate\Support\Str; use Illuminate\Support\Str;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
@ -21,7 +22,8 @@ class SmartPlaylistServiceTest extends PlusTestCase
$this->service = app(SmartPlaylistService::class); $this->service = app(SmartPlaylistService::class);
} }
public function testOwnSongsOnlyOption(): void #[Test]
public function ownSongsOnlyOption(): void
{ {
$owner = create_user(); $owner = create_user();
$matches = Song::factory()->count(3)->for($owner, 'owner')->create(['title' => 'Foo Something']); $matches = Song::factory()->count(3)->for($owner, 'owner')->create(['title' => 'Foo Something']);

View file

@ -11,6 +11,7 @@ use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\Http; use Illuminate\Support\Facades\Http;
use Mockery; use Mockery;
use Mockery\MockInterface; use Mockery\MockInterface;
use PHPUnit\Framework\Attributes\Test;
use Spatie\Dropbox\Client; use Spatie\Dropbox\Client;
use Spatie\FlysystemDropbox\DropboxAdapter; use Spatie\FlysystemDropbox\DropboxAdapter;
use Tests\PlusTestCase; use Tests\PlusTestCase;
@ -49,7 +50,8 @@ class DropboxStorageTest extends PlusTestCase
$this->file = UploadedFile::fromFile(test_path('songs/full.mp3'), 'song.mp3'); //@phpstan-ignore-line $this->file = UploadedFile::fromFile(test_path('songs/full.mp3'), 'song.mp3'); //@phpstan-ignore-line
} }
public function testStoreUploadedFile(): void #[Test]
public function storeUploadedFile(): void
{ {
$this->client->shouldReceive('setAccessToken')->with('free-bird')->once(); $this->client->shouldReceive('setAccessToken')->with('free-bird')->once();
@ -72,7 +74,8 @@ class DropboxStorageTest extends PlusTestCase
self::assertSame('free-bird', Cache::get('dropbox_access_token')); self::assertSame('free-bird', Cache::get('dropbox_access_token'));
} }
public function testAccessTokenCache(): void #[Test]
public function accessTokenCache(): void
{ {
Cache::put('dropbox_access_token', 'cached-token', now()->addHour()); Cache::put('dropbox_access_token', 'cached-token', now()->addHour());
@ -83,7 +86,8 @@ class DropboxStorageTest extends PlusTestCase
Http::assertNothingSent(); Http::assertNothingSent();
} }
public function testGetSongPresignedUrl(): void #[Test]
public function getSongPresignedUrl(): void
{ {
$this->client->allows('setAccessToken'); $this->client->allows('setAccessToken');

View file

@ -6,6 +6,7 @@ use App\Models\Song;
use App\Services\SongStorages\S3CompatibleStorage; use App\Services\SongStorages\S3CompatibleStorage;
use Illuminate\Http\UploadedFile; use Illuminate\Http\UploadedFile;
use Illuminate\Support\Facades\Storage; use Illuminate\Support\Facades\Storage;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
@ -24,7 +25,8 @@ class S3CompatibleStorageTest extends PlusTestCase
$this->file = UploadedFile::fromFile(test_path('songs/full.mp3'), 'song.mp3'); //@phpstan-ignore-line $this->file = UploadedFile::fromFile(test_path('songs/full.mp3'), 'song.mp3'); //@phpstan-ignore-line
} }
public function testStoreUploadedFile(): void #[Test]
public function storeUploadedFile(): void
{ {
self::assertEquals(0, Song::query()->where('storage', 's3')->count()); self::assertEquals(0, Song::query()->where('storage', 's3')->count());
@ -35,7 +37,8 @@ class S3CompatibleStorageTest extends PlusTestCase
self::assertEquals(1, Song::query()->where('storage', 's3')->count()); self::assertEquals(1, Song::query()->where('storage', 's3')->count());
} }
public function testStoringWithVisibilityPreference(): void #[Test]
public function storingWithVisibilityPreference(): void
{ {
$user = create_user(); $user = create_user();
@ -51,7 +54,8 @@ class S3CompatibleStorageTest extends PlusTestCase
self::assertFalse($this->service->storeUploadedFile($privateFile, $user)->is_public); self::assertFalse($this->service->storeUploadedFile($privateFile, $user)->is_public);
} }
public function testDelete(): void #[Test]
public function deleteSong(): void
{ {
Storage::fake('s3'); Storage::fake('s3');
@ -62,7 +66,8 @@ class S3CompatibleStorageTest extends PlusTestCase
Storage::disk('s3')->assertMissing($song->storage_metadata->getPath()); Storage::disk('s3')->assertMissing($song->storage_metadata->getPath());
} }
public function testGetPresignedUrl(): void #[Test]
public function getPresignedUrl(): void
{ {
Storage::fake('s3'); Storage::fake('s3');

View file

@ -6,6 +6,7 @@ use App\Models\Song;
use App\Services\SongStorages\SftpStorage; use App\Services\SongStorages\SftpStorage;
use Illuminate\Http\UploadedFile; use Illuminate\Http\UploadedFile;
use Illuminate\Support\Facades\Storage; use Illuminate\Support\Facades\Storage;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
@ -24,7 +25,8 @@ class SftpStorageTest extends PlusTestCase
$this->file = UploadedFile::fromFile(test_path('songs/full.mp3'), 'song.mp3'); //@phpstan-ignore-line $this->file = UploadedFile::fromFile(test_path('songs/full.mp3'), 'song.mp3'); //@phpstan-ignore-line
} }
public function testStoreUploadedFile(): void #[Test]
public function storeUploadedFile(): void
{ {
self::assertEquals(0, Song::query()->where('storage', 'sftp')->count()); self::assertEquals(0, Song::query()->where('storage', 'sftp')->count());
@ -35,7 +37,8 @@ class SftpStorageTest extends PlusTestCase
self::assertEquals(1, Song::query()->where('storage', 'sftp')->count()); self::assertEquals(1, Song::query()->where('storage', 'sftp')->count());
} }
public function testStoringWithVisibilityPreference(): void #[Test]
public function storingWithVisibilityPreference(): void
{ {
Storage::fake('sftp'); Storage::fake('sftp');
@ -53,7 +56,8 @@ class SftpStorageTest extends PlusTestCase
self::assertFalse($this->service->storeUploadedFile($privateFile, $user)->is_public); self::assertFalse($this->service->storeUploadedFile($privateFile, $user)->is_public);
} }
public function testDelete(): void #[Test]
public function deleteSong(): void
{ {
Storage::fake('sftp'); Storage::fake('sftp');
@ -64,7 +68,8 @@ class SftpStorageTest extends PlusTestCase
Storage::disk('sftp')->assertMissing($song->storage_metadata->getPath()); Storage::disk('sftp')->assertMissing($song->storage_metadata->getPath());
} }
public function testGetSongContent(): void #[Test]
public function getSongContent(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->create(); $song = Song::factory()->create();
@ -75,7 +80,8 @@ class SftpStorageTest extends PlusTestCase
self::assertEquals('binary-content', $this->service->getSongContent($song)); self::assertEquals('binary-content', $this->service->getSongContent($song));
} }
public function testCopyToLocal(): void #[Test]
public function copyToLocal(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->create(); $song = Song::factory()->create();

View file

@ -11,11 +11,13 @@ use App\Services\Streamer\Adapters\SftpStreamerAdapter;
use App\Services\Streamer\Streamer; use App\Services\Streamer\Streamer;
use Exception; use Exception;
use Illuminate\Support\Facades\File; use Illuminate\Support\Facades\File;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
class StreamerTest extends PlusTestCase class StreamerTest extends PlusTestCase
{ {
public function testResolveAdapters(): void #[Test]
public function resolveAdapters(): void
{ {
File::partialMock()->shouldReceive('mimeType')->andReturn('audio/mpeg'); File::partialMock()->shouldReceive('mimeType')->andReturn('audio/mpeg');

View file

@ -8,6 +8,7 @@ use App\Values\SSOUser;
use Illuminate\Support\Facades\Hash; use Illuminate\Support\Facades\Hash;
use Laravel\Socialite\Two\User as SocialiteUser; use Laravel\Socialite\Two\User as SocialiteUser;
use Mockery; use Mockery;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use function Tests\create_user; use function Tests\create_user;
@ -23,7 +24,8 @@ class UserServiceTest extends PlusTestCase
$this->service = app(UserService::class); $this->service = app(UserService::class);
} }
public function testCreateUserViaSSOProvider(): void #[Test]
public function createUserViaSSOProvider(): void
{ {
$user = $this->service->createUser( $user = $this->service->createUser(
name: 'Bruce Dickinson', name: 'Bruce Dickinson',
@ -41,7 +43,8 @@ class UserServiceTest extends PlusTestCase
self::assertSame('https://lh3.googleusercontent.com/a/vatar', $user->avatar); self::assertSame('https://lh3.googleusercontent.com/a/vatar', $user->avatar);
} }
public function testCreateUserFromSSO(): void #[Test]
public function createUserFromSSO(): void
{ {
self::assertDatabaseMissing(User::class, ['email' => 'bruce@iron.com']); self::assertDatabaseMissing(User::class, ['email' => 'bruce@iron.com']);
@ -63,7 +66,8 @@ class UserServiceTest extends PlusTestCase
self::assertSame('https://lh3.googleusercontent.com/a/vatar', $user->avatar); self::assertSame('https://lh3.googleusercontent.com/a/vatar', $user->avatar);
} }
public function testUpdateUserFromSSOId(): void #[Test]
public function updateUserFromSSOId(): void
{ {
$user = create_user([ $user = create_user([
'email' => 'bruce@iron.com', 'email' => 'bruce@iron.com',
@ -88,7 +92,8 @@ class UserServiceTest extends PlusTestCase
self::assertSame('Google', $user->sso_provider); self::assertSame('Google', $user->sso_provider);
} }
public function testUpdateUserFromSSOEmail(): void #[Test]
public function updateUserFromSSOEmail(): void
{ {
$user = create_user([ $user = create_user([
'email' => 'bruce@iron.com', 'email' => 'bruce@iron.com',
@ -111,7 +116,8 @@ class UserServiceTest extends PlusTestCase
self::assertSame('Google', $user->sso_provider); self::assertSame('Google', $user->sso_provider);
} }
public function testUpdateSSOUserCannotChangeProfileDetails(): void #[Test]
public function updateSSOUserCannotChangeProfileDetails(): void
{ {
$user = create_user([ $user = create_user([
'email' => 'bruce@iron.com', 'email' => 'bruce@iron.com',

View file

@ -9,6 +9,7 @@ use App\Models\Song;
use App\Values\ScanResult; use App\Values\ScanResult;
use App\Values\ScanResultCollection; use App\Values\ScanResultCollection;
use Illuminate\Database\Eloquent\Collection; use Illuminate\Database\Eloquent\Collection;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class DeleteNonExistingRecordsPostSyncTest extends TestCase class DeleteNonExistingRecordsPostSyncTest extends TestCase
@ -22,7 +23,8 @@ class DeleteNonExistingRecordsPostSyncTest extends TestCase
$this->listener = app(DeleteNonExistingRecordsPostScan::class); $this->listener = app(DeleteNonExistingRecordsPostScan::class);
} }
public function testHandleDoesNotDeleteCloudEntries(): void #[Test]
public function handleDoesNotDeleteCloudEntries(): void
{ {
collect(SongStorageType::cases()) collect(SongStorageType::cases())
->filter(static fn ($type) => $type !== SongStorageType::LOCAL) ->filter(static fn ($type) => $type !== SongStorageType::LOCAL)
@ -34,14 +36,16 @@ class DeleteNonExistingRecordsPostSyncTest extends TestCase
}); });
} }
public function testHandleDoesNotDeleteEpisodes(): void #[Test]
public function handleDoesNotDeleteEpisodes(): void
{ {
$episode = Song::factory()->asEpisode()->create(); $episode = Song::factory()->asEpisode()->create();
$this->listener->handle(new MediaScanCompleted(ScanResultCollection::create())); $this->listener->handle(new MediaScanCompleted(ScanResultCollection::create()));
self::assertModelExists($episode); self::assertModelExists($episode);
} }
public function testHandle(): void #[Test]
public function handle(): void
{ {
/** @var Collection|array<array-key, Song> $songs */ /** @var Collection|array<array-key, Song> $songs */
$songs = Song::factory(4)->create(); $songs = Song::factory(4)->create();

View file

@ -4,13 +4,15 @@ namespace Tests\Integration\Models;
use App\Models\Song; use App\Models\Song;
use App\Models\SongZipArchive; use App\Models\SongZipArchive;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\test_path; use function Tests\test_path;
class SongZipArchiveTest extends TestCase class SongZipArchiveTest extends TestCase
{ {
public function testAddSongIntoArchive(): void #[Test]
public function addSongIntoArchive(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->create(['path' => test_path('songs/full.mp3')]); $song = Song::factory()->create(['path' => test_path('songs/full.mp3')]);
@ -22,7 +24,8 @@ class SongZipArchiveTest extends TestCase
self::assertSame('full.mp3', $songZipArchive->getArchive()->getNameIndex(0)); self::assertSame('full.mp3', $songZipArchive->getArchive()->getNameIndex(0));
} }
public function testAddMultipleSongsIntoArchive(): void #[Test]
public function addMultipleSongsIntoArchive(): void
{ {
$songs = collect([ $songs = collect([
Song::factory()->create(['path' => test_path('songs/full.mp3')]), Song::factory()->create(['path' => test_path('songs/full.mp3')]),

View file

@ -4,6 +4,7 @@ namespace Tests\Integration\Repositories;
use App\Models\Song; use App\Models\Song;
use App\Repositories\SongRepository; use App\Repositories\SongRepository;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class SongRepositoryTest extends TestCase class SongRepositoryTest extends TestCase
@ -17,7 +18,8 @@ class SongRepositoryTest extends TestCase
$this->songRepository = app(SongRepository::class); $this->songRepository = app(SongRepository::class);
} }
public function testGetOneByPath(): void #[Test]
public function getOneByPath(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->create(['path' => 'foo']); $song = Song::factory()->create(['path' => 'foo']);

View file

@ -8,13 +8,15 @@ use GuzzleHttp\Handler\MockHandler;
use GuzzleHttp\HandlerStack; use GuzzleHttp\HandlerStack;
use GuzzleHttp\Psr7\Response; use GuzzleHttp\Psr7\Response;
use Illuminate\Support\Facades\File; use Illuminate\Support\Facades\File;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\test_path; use function Tests\test_path;
class ApplicationInformationServiceTest extends TestCase class ApplicationInformationServiceTest extends TestCase
{ {
public function testGetLatestVersionNumber(): void #[Test]
public function getLatestVersionNumber(): void
{ {
$latestVersion = 'v1.1.2'; $latestVersion = 'v1.1.2';

View file

@ -7,6 +7,7 @@ use Illuminate\Auth\Events\PasswordReset;
use Illuminate\Support\Facades\Event; use Illuminate\Support\Facades\Event;
use Illuminate\Support\Facades\Hash; use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Password; use Illuminate\Support\Facades\Password;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
@ -22,7 +23,8 @@ class AuthenticationServiceTest extends TestCase
$this->service = app(AuthenticationService::class); $this->service = app(AuthenticationService::class);
} }
public function testTryResetPasswordUsingBroker(): void #[Test]
public function tryResetPasswordUsingBroker(): void
{ {
Event::fake(); Event::fake();
$user = create_user(); $user = create_user();
@ -36,7 +38,8 @@ class AuthenticationServiceTest extends TestCase
Event::assertDispatched(PasswordReset::class); Event::assertDispatched(PasswordReset::class);
} }
public function testTryResetPasswordUsingBrokerWithInvalidToken(): void #[Test]
public function tryResetPasswordUsingBrokerWithInvalidToken(): void
{ {
Event::fake(); Event::fake();
$user = create_user(['password' => Hash::make('old-password')]); $user = create_user(['password' => Hash::make('old-password')]);

View file

@ -5,6 +5,7 @@ namespace Tests\Integration\Services;
use App\Services\FileScanner; use App\Services\FileScanner;
use Illuminate\Support\Facades\File; use Illuminate\Support\Facades\File;
use Illuminate\Support\Str; use Illuminate\Support\Str;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\test_path; use function Tests\test_path;
@ -20,7 +21,8 @@ class FileScannerTest extends TestCase
$this->scanner = app(FileScanner::class); $this->scanner = app(FileScanner::class);
} }
public function testGetFileInfo(): void #[Test]
public function getFileInfo(): void
{ {
$info = $this->scanner->setFile(test_path('songs/full.mp3'))->getScanInformation(); $info = $this->scanner->setFile(test_path('songs/full.mp3'))->getScanInformation();
@ -50,7 +52,8 @@ class FileScannerTest extends TestCase
self::assertEqualsWithDelta(10, $info->length, 0.1); self::assertEqualsWithDelta(10, $info->length, 0.1);
} }
public function testGetFileInfoVorbisCommentsFlac(): void #[Test]
public function getFileInfoVorbisCommentsFlac(): void
{ {
$flacPath = test_path('songs/full-vorbis-comments.flac'); $flacPath = test_path('songs/full-vorbis-comments.flac');
$info = $this->scanner->setFile($flacPath)->getScanInformation(); $info = $this->scanner->setFile($flacPath)->getScanInformation();
@ -79,14 +82,16 @@ class FileScannerTest extends TestCase
self::assertEqualsWithDelta(10, $info->length, 0.1); self::assertEqualsWithDelta(10, $info->length, 0.1);
} }
public function testSongWithoutTitleHasFileNameAsTitle(): void #[Test]
public function songWithoutTitleHasFileNameAsTitle(): void
{ {
$this->scanner->setFile(test_path('songs/blank.mp3')); $this->scanner->setFile(test_path('songs/blank.mp3'));
self::assertSame('blank', $this->scanner->getScanInformation()->title); self::assertSame('blank', $this->scanner->getScanInformation()->title);
} }
public function testIgnoreLrcFileIfEmbeddedLyricsAvailable(): void #[Test]
public function ignoreLrcFileIfEmbeddedLyricsAvailable(): void
{ {
$base = sys_get_temp_dir() . '/' . Str::uuid(); $base = sys_get_temp_dir() . '/' . Str::uuid();
$mediaFile = $base . '.mp3'; $mediaFile = $base . '.mp3';
@ -97,7 +102,8 @@ class FileScannerTest extends TestCase
self::assertSame("Foo\rbar", $this->scanner->setFile($mediaFile)->getScanInformation()->lyrics); self::assertSame("Foo\rbar", $this->scanner->setFile($mediaFile)->getScanInformation()->lyrics);
} }
public function testReadLrcFileIfEmbeddedLyricsNotAvailable(): void #[Test]
public function readLrcFileIfEmbeddedLyricsNotAvailable(): void
{ {
$base = sys_get_temp_dir() . '/' . Str::uuid(); $base = sys_get_temp_dir() . '/' . Str::uuid();
$mediaFile = $base . '.mp3'; $mediaFile = $base . '.mp3';

View file

@ -7,6 +7,7 @@ use App\Models\Album;
use App\Models\Artist; use App\Models\Artist;
use App\Services\ITunesService; use App\Services\ITunesService;
use Illuminate\Support\Facades\Cache; use Illuminate\Support\Facades\Cache;
use PHPUnit\Framework\Attributes\Test;
use Saloon\Http\Faking\MockResponse; use Saloon\Http\Faking\MockResponse;
use Saloon\Laravel\Saloon; use Saloon\Laravel\Saloon;
use Tests\TestCase; use Tests\TestCase;
@ -22,7 +23,8 @@ class ITunesServiceTest extends TestCase
$this->service = app(ITunesService::class); $this->service = app(ITunesService::class);
} }
public function testConfiguration(): void #[Test]
public function configuration(): void
{ {
config(['koel.itunes.enabled' => true]); config(['koel.itunes.enabled' => true]);
self::assertTrue($this->service->used()); self::assertTrue($this->service->used());
@ -31,7 +33,8 @@ class ITunesServiceTest extends TestCase
self::assertFalse($this->service->used()); self::assertFalse($this->service->used());
} }
public function testGetTrackUrl(): void #[Test]
public function getTrackUrl(): void
{ {
config(['koel.itunes.enabled' => true]); config(['koel.itunes.enabled' => true]);
config(['koel.itunes.affiliate_id' => 'foo']); config(['koel.itunes.affiliate_id' => 'foo']);

View file

@ -10,6 +10,7 @@ use App\Models\Song;
use App\Services\InteractionService; use App\Services\InteractionService;
use Illuminate\Support\Collection; use Illuminate\Support\Collection;
use Illuminate\Support\Facades\Event; use Illuminate\Support\Facades\Event;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
@ -25,7 +26,8 @@ class InteractionServiceTest extends TestCase
$this->interactionService = new InteractionService(); $this->interactionService = new InteractionService();
} }
public function testIncreasePlayCount(): void #[Test]
public function increasePlayCount(): void
{ {
/** @var Interaction $interaction */ /** @var Interaction $interaction */
$interaction = Interaction::factory()->create(); $interaction = Interaction::factory()->create();
@ -35,7 +37,8 @@ class InteractionServiceTest extends TestCase
self::assertSame($currentCount + 1, $interaction->refresh()->play_count); self::assertSame($currentCount + 1, $interaction->refresh()->play_count);
} }
public function testToggleLike(): void #[Test]
public function toggleLike(): void
{ {
Event::fake(SongLikeToggled::class); Event::fake(SongLikeToggled::class);
@ -49,7 +52,8 @@ class InteractionServiceTest extends TestCase
Event::assertDispatched(SongLikeToggled::class); Event::assertDispatched(SongLikeToggled::class);
} }
public function testLikeMultipleSongs(): void #[Test]
public function likeMultipleSongs(): void
{ {
Event::fake(MultipleSongsLiked::class); Event::fake(MultipleSongsLiked::class);
@ -72,7 +76,8 @@ class InteractionServiceTest extends TestCase
Event::assertDispatched(MultipleSongsLiked::class); Event::assertDispatched(MultipleSongsLiked::class);
} }
public function testUnlikeMultipleSongs(): void #[Test]
public function unlikeMultipleSongs(): void
{ {
Event::fake(MultipleSongsUnliked::class); Event::fake(MultipleSongsUnliked::class);
$user = create_user(); $user = create_user();

View file

@ -12,6 +12,8 @@ use App\Models\Artist;
use App\Models\Song; use App\Models\Song;
use App\Services\LastfmService; use App\Services\LastfmService;
use Illuminate\Support\Facades\File; use Illuminate\Support\Facades\File;
use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\Attributes\Test;
use Saloon\Http\Faking\MockResponse; use Saloon\Http\Faking\MockResponse;
use Saloon\Laravel\Saloon; use Saloon\Laravel\Saloon;
use Tests\TestCase; use Tests\TestCase;
@ -35,7 +37,8 @@ class LastfmServiceTest extends TestCase
$this->service = app(LastfmService::class); $this->service = app(LastfmService::class);
} }
public function testGetArtistInformation(): void #[Test]
public function getArtistInformation(): void
{ {
/** @var Artist $artist */ /** @var Artist $artist */
$artist = Artist::factory()->make(['name' => 'Kamelot']); $artist = Artist::factory()->make(['name' => 'Kamelot']);
@ -67,7 +70,8 @@ class LastfmServiceTest extends TestCase
], $info->toArray()); ], $info->toArray());
} }
public function testGetArtistInformationForNonExistentArtist(): void #[Test]
public function getArtistInformationForNonExistentArtist(): void
{ {
/** @var Artist $artist */ /** @var Artist $artist */
$artist = Artist::factory()->make(['name' => 'bar']); $artist = Artist::factory()->make(['name' => 'bar']);
@ -81,7 +85,8 @@ class LastfmServiceTest extends TestCase
self::assertNull($this->service->getArtistInformation($artist)); self::assertNull($this->service->getArtistInformation($artist));
} }
public function testGetAlbumInformation(): void #[Test]
public function getAlbumInformation(): void
{ {
/** @var Album $album */ /** @var Album $album */
$album = Album::factory()->for(Artist::factory()->create(['name' => 'Kamelot']))->create(['name' => 'Epica']); $album = Album::factory()->for(Artist::factory()->create(['name' => 'Kamelot']))->create(['name' => 'Epica']);
@ -126,7 +131,8 @@ class LastfmServiceTest extends TestCase
], $info->toArray()); ], $info->toArray());
} }
public function testGetAlbumInformationForNonExistentAlbum(): void #[Test]
public function getAlbumInformationForNonExistentAlbum(): void
{ {
/** @var Album $album */ /** @var Album $album */
$album = Album::factory()->for(Artist::factory()->create(['name' => 'Kamelot']))->create(['name' => 'Foo']); $album = Album::factory()->for(Artist::factory()->create(['name' => 'Kamelot']))->create(['name' => 'Foo']);
@ -140,7 +146,8 @@ class LastfmServiceTest extends TestCase
self::assertNull($this->service->getAlbumInformation($album)); self::assertNull($this->service->getAlbumInformation($album));
} }
public function testScrobble(): void #[Test]
public function scrobble(): void
{ {
$user = create_user([ $user = create_user([
'preferences' => [ 'preferences' => [
@ -175,8 +182,9 @@ class LastfmServiceTest extends TestCase
return [[true, 'track.love'], [false, 'track.unlove']]; return [[true, 'track.love'], [false, 'track.unlove']];
} }
/** @dataProvider provideToggleLoveTrackData */ #[DataProvider('provideToggleLoveTrackData')]
public function testToggleLoveTrack(bool $love, string $method): void #[Test]
public function toggleLoveTrack(bool $love, string $method): void
{ {
$user = create_user([ $user = create_user([
'preferences' => [ 'preferences' => [
@ -203,7 +211,8 @@ class LastfmServiceTest extends TestCase
}); });
} }
public function testUpdateNowPlaying(): void #[Test]
public function updateNowPlaying(): void
{ {
$user = create_user([ $user = create_user([
'preferences' => [ 'preferences' => [

View file

@ -12,6 +12,7 @@ use App\Values\LicenseStatus;
use Illuminate\Http\Response; use Illuminate\Http\Response;
use Illuminate\Support\Facades\Cache; use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\File; use Illuminate\Support\Facades\File;
use PHPUnit\Framework\Attributes\Test;
use Saloon\Http\Faking\MockResponse; use Saloon\Http\Faking\MockResponse;
use Saloon\Laravel\Facades\Saloon; use Saloon\Laravel\Facades\Saloon;
use Tests\TestCase; use Tests\TestCase;
@ -29,7 +30,8 @@ class LicenseServiceTest extends TestCase
$this->service = app(LicenseService::class); $this->service = app(LicenseService::class);
} }
public function testActivateLicense(): void #[Test]
public function activateLicense(): void
{ {
config(['lemonsqueezy.store_id' => 42]); config(['lemonsqueezy.store_id' => 42]);
$key = '38b1460a-5104-4067-a91d-77b872934d51'; $key = '38b1460a-5104-4067-a91d-77b872934d51';
@ -63,7 +65,8 @@ class LicenseServiceTest extends TestCase
}); });
} }
public function testActivateLicenseFailsBecauseOfIncorrectStoreId(): void #[Test]
public function activateLicenseFailsBecauseOfIncorrectStoreId(): void
{ {
$this->expectException(FailedToActivateLicenseException::class); $this->expectException(FailedToActivateLicenseException::class);
$this->expectExceptionMessage('This license key is not from Koels official store.'); $this->expectExceptionMessage('This license key is not from Koels official store.');
@ -80,7 +83,8 @@ class LicenseServiceTest extends TestCase
$this->service->activate($key); $this->service->activate($key);
} }
public function testActivateLicenseFailsForInvalidLicenseKey(): void #[Test]
public function activateLicenseFailsForInvalidLicenseKey(): void
{ {
$this->expectException(FailedToActivateLicenseException::class); $this->expectException(FailedToActivateLicenseException::class);
$this->expectExceptionMessage('license_key not found'); $this->expectExceptionMessage('license_key not found');
@ -95,7 +99,8 @@ class LicenseServiceTest extends TestCase
$this->service->activate('invalid-key'); $this->service->activate('invalid-key');
} }
public function testDeactivateLicense(): void #[Test]
public function deactivateLicense(): void
{ {
/** @var License $license */ /** @var License $license */
$license = License::factory()->create(); $license = License::factory()->create();
@ -122,7 +127,8 @@ class LicenseServiceTest extends TestCase
}); });
} }
public function testDeactivateLicenseHandlesLeftoverRecords(): void #[Test]
public function deactivateLicenseHandlesLeftoverRecords(): void
{ {
/** @var License $license */ /** @var License $license */
$license = License::factory()->create(); $license = License::factory()->create();
@ -133,7 +139,8 @@ class LicenseServiceTest extends TestCase
self::assertModelMissing($license); self::assertModelMissing($license);
} }
public function testDeactivateLicenseFails(): void #[Test]
public function deactivateLicenseFails(): void
{ {
$this->expectExceptionMessage('Unprocessable Entity (422) Response: Something went horrible wrong'); $this->expectExceptionMessage('Unprocessable Entity (422) Response: Something went horrible wrong');
@ -150,7 +157,8 @@ class LicenseServiceTest extends TestCase
$this->service->deactivate($license); $this->service->deactivate($license);
} }
public function testGetLicenseStatusFromCache(): void #[Test]
public function getLicenseStatusFromCache(): void
{ {
Saloon::fake([]); Saloon::fake([]);
@ -165,7 +173,8 @@ class LicenseServiceTest extends TestCase
Saloon::assertNothingSent(); Saloon::assertNothingSent();
} }
public function testGetLicenseStatusWithNoLicenses(): void #[Test]
public function getLicenseStatusWithNoLicenses(): void
{ {
Saloon::fake([]); Saloon::fake([]);
License::query()->delete(); License::query()->delete();
@ -174,7 +183,8 @@ class LicenseServiceTest extends TestCase
Saloon::assertNothingSent(); Saloon::assertNothingSent();
} }
public function testGetLicenseStatusValidatesWithApi(): void #[Test]
public function getLicenseStatusValidatesWithApi(): void
{ {
/** @var License $license */ /** @var License $license */
$license = License::factory()->create(); $license = License::factory()->create();
@ -200,7 +210,8 @@ class LicenseServiceTest extends TestCase
}); });
} }
public function testGetLicenseStatusValidatesWithApiWithInvalidLicense(): void #[Test]
public function getLicenseStatusValidatesWithApiWithInvalidLicense(): void
{ {
License::factory()->create(); License::factory()->create();

View file

@ -5,6 +5,7 @@ namespace Tests\Integration\Services;
use App\Models\Album; use App\Models\Album;
use App\Services\MediaMetadataService; use App\Services\MediaMetadataService;
use Illuminate\Support\Facades\File; use Illuminate\Support\Facades\File;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\test_path; use function Tests\test_path;
@ -18,7 +19,8 @@ class MediaMetadataServiceTest extends TestCase
$this->cleanUp(); $this->cleanUp();
} }
public function testGetAlbumThumbnailUrl(): void #[Test]
public function getAlbumThumbnailUrl(): void
{ {
File::copy(test_path('blobs/cover.png'), album_cover_path('album-cover-for-thumbnail-test.jpg')); File::copy(test_path('blobs/cover.png'), album_cover_path('album-cover-for-thumbnail-test.jpg'));
@ -33,7 +35,8 @@ class MediaMetadataServiceTest extends TestCase
self::assertFileExists(album_cover_path('album-cover-for-thumbnail-test_thumb.jpg')); self::assertFileExists(album_cover_path('album-cover-for-thumbnail-test_thumb.jpg'));
} }
public function testGetAlbumThumbnailUrlWithNoCover(): void #[Test]
public function getAlbumThumbnailUrlWithNoCover(): void
{ {
/** @var Album $album */ /** @var Album $album */
$album = Album::factory()->create(['cover' => '']); $album = Album::factory()->create(['cover' => '']);

View file

@ -15,6 +15,7 @@ use getID3;
use Illuminate\Support\Arr; use Illuminate\Support\Arr;
use Illuminate\Support\Facades\Event; use Illuminate\Support\Facades\Event;
use Mockery; use Mockery;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
@ -36,7 +37,8 @@ class MediaScannerTest extends TestCase
return realpath($this->mediaPath . $subPath); return realpath($this->mediaPath . $subPath);
} }
public function testScan(): void #[Test]
public function scan(): void
{ {
Event::fake(MediaScanCompleted::class); Event::fake(MediaScanCompleted::class);
@ -93,7 +95,8 @@ class MediaScannerTest extends TestCase
self::assertSame('Cuckoo', $song->artist->name); self::assertSame('Cuckoo', $song->artist->name);
} }
public function testModifiedFileIsRescanned(): void #[Test]
public function modifiedFileIsRescanned(): void
{ {
$config = ScanConfiguration::make(owner: create_admin()); $config = ScanConfiguration::make(owner: create_admin());
$this->scanner->scan($config); $this->scanner->scan($config);
@ -107,7 +110,8 @@ class MediaScannerTest extends TestCase
self::assertSame($time, $song->refresh()->mtime); self::assertSame($time, $song->refresh()->mtime);
} }
public function testRescanWithoutForceDoesNotResetData(): void #[Test]
public function rescanWithoutForceDoesNotResetData(): void
{ {
Event::fake(MediaScanCompleted::class); Event::fake(MediaScanCompleted::class);
@ -130,7 +134,8 @@ class MediaScannerTest extends TestCase
self::assertSame('Booom Wroooom', $song->lyrics); self::assertSame('Booom Wroooom', $song->lyrics);
} }
public function testForceScanResetsData(): void #[Test]
public function forceScanResetsData(): void
{ {
Event::fake(MediaScanCompleted::class); Event::fake(MediaScanCompleted::class);
@ -155,7 +160,8 @@ class MediaScannerTest extends TestCase
self::assertSame($owner->id, $song->owner_id); self::assertSame($owner->id, $song->owner_id);
} }
public function testScanWithIgnoredTags(): void #[Test]
public function scanWithIgnoredTags(): void
{ {
Event::fake(MediaScanCompleted::class); Event::fake(MediaScanCompleted::class);
@ -178,7 +184,8 @@ class MediaScannerTest extends TestCase
self::assertNotSame('Booom Wroooom', $song->lyrics); self::assertNotSame('Booom Wroooom', $song->lyrics);
} }
public function testScanAllTagsForNewFilesRegardlessOfIgnoredOption(): void #[Test]
public function scanAllTagsForNewFilesRegardlessOfIgnoredOption(): void
{ {
Event::fake(MediaScanCompleted::class); Event::fake(MediaScanCompleted::class);
@ -203,7 +210,8 @@ class MediaScannerTest extends TestCase
); );
} }
public function testScanAddedSongViaWatch(): void #[Test]
public function scanAddedSongViaWatch(): void
{ {
$path = $this->path('/blank.mp3'); $path = $this->path('/blank.mp3');
@ -215,7 +223,8 @@ class MediaScannerTest extends TestCase
self::assertDatabaseHas(Song::class, ['path' => $path]); self::assertDatabaseHas(Song::class, ['path' => $path]);
} }
public function testScanDeletedSongViaWatch(): void #[Test]
public function scanDeletedSongViaWatch(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->create(); $song = Song::factory()->create();
@ -228,7 +237,8 @@ class MediaScannerTest extends TestCase
self::assertModelMissing($song); self::assertModelMissing($song);
} }
public function testScanDeletedDirectoryViaWatch(): void #[Test]
public function scanDeletedDirectoryViaWatch(): void
{ {
Event::fake(MediaScanCompleted::class); Event::fake(MediaScanCompleted::class);
@ -242,7 +252,8 @@ class MediaScannerTest extends TestCase
self::assertDatabaseMissing(Song::class, ['path' => $this->path('/subdir/back-in-black.mp3')]); self::assertDatabaseMissing(Song::class, ['path' => $this->path('/subdir/back-in-black.mp3')]);
} }
public function testHtmlEntities(): void #[Test]
public function htmlEntities(): void
{ {
$path = $this->path('/songs/blank.mp3'); $path = $this->path('/songs/blank.mp3');
$analyzed = [ $analyzed = [
@ -275,7 +286,8 @@ class MediaScannerTest extends TestCase
self::assertSame('水谷広実', $info->title); self::assertSame('水谷広実', $info->title);
} }
public function testOptionallyIgnoreHiddenFiles(): void #[Test]
public function optionallyIgnoreHiddenFiles(): void
{ {
$config = ScanConfiguration::make(owner: create_admin()); $config = ScanConfiguration::make(owner: create_admin());

View file

@ -10,6 +10,7 @@ use App\Services\PlaylistService;
use App\Values\SmartPlaylistRuleGroupCollection; use App\Values\SmartPlaylistRuleGroupCollection;
use Illuminate\Support\Collection; use Illuminate\Support\Collection;
use InvalidArgumentException as BaseInvalidArgumentException; use InvalidArgumentException as BaseInvalidArgumentException;
use PHPUnit\Framework\Attributes\Test;
use Tests\PlusTestCase; use Tests\PlusTestCase;
use Tests\TestCase; use Tests\TestCase;
use Webmozart\Assert\InvalidArgumentException; use Webmozart\Assert\InvalidArgumentException;
@ -27,7 +28,8 @@ class PlaylistServiceTest extends TestCase
$this->service = app(PlaylistService::class); $this->service = app(PlaylistService::class);
} }
public function testCreatePlaylist(): void #[Test]
public function createPlaylist(): void
{ {
$user = create_user(); $user = create_user();
@ -38,7 +40,8 @@ class PlaylistServiceTest extends TestCase
self::assertFalse($playlist->is_smart); self::assertFalse($playlist->is_smart);
} }
public function testCreatePlaylistWithSongs(): void #[Test]
public function createPlaylistWithSongs(): void
{ {
/** @var Collection<array-key, Song> $songs */ /** @var Collection<array-key, Song> $songs */
$songs = Song::factory(3)->create(); $songs = Song::factory(3)->create();
@ -53,7 +56,8 @@ class PlaylistServiceTest extends TestCase
self::assertEqualsCanonicalizing($playlist->playables->pluck('id')->all(), $songs->pluck('id')->all()); self::assertEqualsCanonicalizing($playlist->playables->pluck('id')->all(), $songs->pluck('id')->all());
} }
public function testCreateSmartPlaylist(): void #[Test]
public function createSmartPlaylist(): void
{ {
$rules = SmartPlaylistRuleGroupCollection::create([ $rules = SmartPlaylistRuleGroupCollection::create([
[ [
@ -78,7 +82,8 @@ class PlaylistServiceTest extends TestCase
self::assertTrue($playlist->is_smart); self::assertTrue($playlist->is_smart);
} }
public function testCreatePlaylistInFolder(): void #[Test]
public function createPlaylistInFolder(): void
{ {
/** @var PlaylistFolder $folder */ /** @var PlaylistFolder $folder */
$folder = PlaylistFolder::factory()->create(); $folder = PlaylistFolder::factory()->create();
@ -90,7 +95,8 @@ class PlaylistServiceTest extends TestCase
self::assertTrue($playlist->inFolder($folder)); self::assertTrue($playlist->inFolder($folder));
} }
public function testCreatePlaylistInAnotherUsersFolder(): void #[Test]
public function createPlaylistInAnotherUsersFolder(): void
{ {
/** @var PlaylistFolder $folder */ /** @var PlaylistFolder $folder */
$folder = PlaylistFolder::factory()->create(); $folder = PlaylistFolder::factory()->create();
@ -100,7 +106,8 @@ class PlaylistServiceTest extends TestCase
$this->service->createPlaylist('foo', create_user(), $folder); $this->service->createPlaylist('foo', create_user(), $folder);
} }
public function testUpdateSimplePlaylist(): void #[Test]
public function updateSimplePlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(['name' => 'foo']); $playlist = Playlist::factory()->create(['name' => 'foo']);
@ -110,7 +117,8 @@ class PlaylistServiceTest extends TestCase
self::assertSame('bar', $playlist->name); self::assertSame('bar', $playlist->name);
} }
public function testUpdateSmartPlaylist(): void #[Test]
public function updateSmartPlaylist(): void
{ {
$rules = SmartPlaylistRuleGroupCollection::create([ $rules = SmartPlaylistRuleGroupCollection::create([
[ [
@ -150,7 +158,8 @@ class PlaylistServiceTest extends TestCase
self::assertSame($playlist->rule_groups->first()->rules->first()->value, ['bar']); self::assertSame($playlist->rule_groups->first()->rules->first()->value, ['bar']);
} }
public function testSettingOwnsSongOnlyFailsForCommunityLicenseWhenCreate(): void #[Test]
public function settingOwnsSongOnlyFailsForCommunityLicenseWhenCreate(): void
{ {
$this->expectException(BaseInvalidArgumentException::class); $this->expectException(BaseInvalidArgumentException::class);
$this->expectExceptionMessage('"Own songs only" option only works with smart playlists and Plus license.'); $this->expectExceptionMessage('"Own songs only" option only works with smart playlists and Plus license.');
@ -175,7 +184,8 @@ class PlaylistServiceTest extends TestCase
); );
} }
public function testSettingOwnsSongOnlyFailsForCommunityLicenseWhenUpdate(): void #[Test]
public function settingOwnsSongOnlyFailsForCommunityLicenseWhenUpdate(): void
{ {
$this->expectException(BaseInvalidArgumentException::class); $this->expectException(BaseInvalidArgumentException::class);
$this->expectExceptionMessage('"Own songs only" option only works with smart playlists and Plus license.'); $this->expectExceptionMessage('"Own songs only" option only works with smart playlists and Plus license.');
@ -190,7 +200,8 @@ class PlaylistServiceTest extends TestCase
); );
} }
public function testAddSongsToPlaylist(): void #[Test]
public function addSongsToPlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -206,7 +217,8 @@ class PlaylistServiceTest extends TestCase
$songs->each(static fn (Song $song) => self::assertTrue($playlist->playables->contains($song))); $songs->each(static fn (Song $song) => self::assertTrue($playlist->playables->contains($song)));
} }
public function testAddEpisodesToPlaylist(): void #[Test]
public function addEpisodesToPlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -226,7 +238,8 @@ class PlaylistServiceTest extends TestCase
self::assertEqualsCanonicalizing($addedEpisodes->pluck('id')->all(), $episodes->pluck('id')->all()); self::assertEqualsCanonicalizing($addedEpisodes->pluck('id')->all(), $episodes->pluck('id')->all());
} }
public function testAddMixOfSongsAndEpisodesToPlaylist(): void #[Test]
public function addMixOfSongsAndEpisodesToPlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -242,7 +255,8 @@ class PlaylistServiceTest extends TestCase
self::assertEqualsCanonicalizing($addedEpisodes->pluck('id')->all(), $playables->pluck('id')->all()); self::assertEqualsCanonicalizing($addedEpisodes->pluck('id')->all(), $playables->pluck('id')->all());
} }
public function testPrivateSongsAreMadePublicWhenAddedToCollaborativePlaylist(): void #[Test]
public function privateSongsAreMadePublicWhenAddedToCollaborativePlaylist(): void
{ {
PlusTestCase::enablePlusLicense(); PlusTestCase::enablePlusLicense();
@ -260,7 +274,8 @@ class PlaylistServiceTest extends TestCase
$songs->each(static fn (Song $song) => self::assertTrue($song->refresh()->is_public)); $songs->each(static fn (Song $song) => self::assertTrue($song->refresh()->is_public));
} }
public function testMakePlaylistSongsPublic(): void #[Test]
public function makePlaylistSongsPublic(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();
@ -271,7 +286,8 @@ class PlaylistServiceTest extends TestCase
$playlist->playables->each(static fn (Song $song) => self::assertTrue($song->is_public)); $playlist->playables->each(static fn (Song $song) => self::assertTrue($song->is_public));
} }
public function testMoveSongsInPlaylist(): void #[Test]
public function moveSongsInPlaylist(): void
{ {
/** @var Playlist $playlist */ /** @var Playlist $playlist */
$playlist = Playlist::factory()->create(); $playlist = Playlist::factory()->create();

View file

@ -12,6 +12,7 @@ use GuzzleHttp\Handler\MockHandler;
use GuzzleHttp\HandlerStack; use GuzzleHttp\HandlerStack;
use GuzzleHttp\Psr7\Response; use GuzzleHttp\Psr7\Response;
use Illuminate\Support\Facades\Http; use Illuminate\Support\Facades\Http;
use PHPUnit\Framework\Attributes\Test;
use Psr\Http\Client\ClientInterface; use Psr\Http\Client\ClientInterface;
use Tests\TestCase; use Tests\TestCase;
@ -36,7 +37,8 @@ class PodcastServiceTest extends TestCase
$this->service = app(PodcastService::class); $this->service = app(PodcastService::class);
} }
public function testAddPodcast(): void #[Test]
public function addPodcast(): void
{ {
$url = 'https://example.com/feed.xml'; $url = 'https://example.com/feed.xml';
$user = create_user(); $user = create_user();
@ -57,7 +59,8 @@ class PodcastServiceTest extends TestCase
self::assertCount(8, $podcast->episodes); self::assertCount(8, $podcast->episodes);
} }
public function testSubscribeUserToPodcast(): void #[Test]
public function subscribeUserToPodcast(): void
{ {
/** @var Podcast $podcast */ /** @var Podcast $podcast */
$podcast = Podcast::factory()->create([ $podcast = Podcast::factory()->create([
@ -76,7 +79,8 @@ class PodcastServiceTest extends TestCase
self::assertSame('My Cool Podcast', $podcast->fresh()->title); self::assertSame('My Cool Podcast', $podcast->fresh()->title);
} }
public function testResubscribeUserToPodcastThrows(): void #[Test]
public function resubscribeUserToPodcastThrows(): void
{ {
self::expectException(UserAlreadySubscribedToPodcast::class); self::expectException(UserAlreadySubscribedToPodcast::class);
@ -91,7 +95,8 @@ class PodcastServiceTest extends TestCase
$this->service->addPodcast('https://example.com/feed.xml', $user); $this->service->addPodcast('https://example.com/feed.xml', $user);
} }
public function testAddingRefreshesObsoletePodcast(): void #[Test]
public function addingRefreshesObsoletePodcast(): void
{ {
self::expectException(UserAlreadySubscribedToPodcast::class); self::expectException(UserAlreadySubscribedToPodcast::class);
@ -117,7 +122,8 @@ class PodcastServiceTest extends TestCase
self::assertSame('Podcast Feed Parser', $podcast->title); self::assertSame('Podcast Feed Parser', $podcast->title);
} }
public function testUnsubscribeUserFromPodcast(): void #[Test]
public function unsubscribeUserFromPodcast(): void
{ {
/** @var Podcast $podcast */ /** @var Podcast $podcast */
$podcast = Podcast::factory()->create(); $podcast = Podcast::factory()->create();
@ -129,7 +135,8 @@ class PodcastServiceTest extends TestCase
self::assertFalse($user->subscribedToPodcast($podcast)); self::assertFalse($user->subscribedToPodcast($podcast));
} }
public function testPodcastNotObsoleteIfSyncedRecently(): void #[Test]
public function podcastNotObsoleteIfSyncedRecently(): void
{ {
/** @var Podcast $podcast */ /** @var Podcast $podcast */
$podcast = Podcast::factory()->create([ $podcast = Podcast::factory()->create([
@ -139,7 +146,8 @@ class PodcastServiceTest extends TestCase
self::assertFalse($this->service->isPodcastObsolete($podcast)); self::assertFalse($this->service->isPodcastObsolete($podcast));
} }
public function testPodcastObsoleteIfModifiedSinceLastSync(): void #[Test]
public function podcastObsoleteIfModifiedSinceLastSync(): void
{ {
Http::fake([ Http::fake([
'https://example.com/feed.xml' => Http::response(headers: ['Last-Modified' => now()->toRfc1123String()]), 'https://example.com/feed.xml' => Http::response(headers: ['Last-Modified' => now()->toRfc1123String()]),
@ -154,7 +162,8 @@ class PodcastServiceTest extends TestCase
self::assertTrue($this->service->isPodcastObsolete($podcast)); self::assertTrue($this->service->isPodcastObsolete($podcast));
} }
public function testUpdateEpisodeProgress(): void #[Test]
public function updateEpisodeProgress(): void
{ {
/** @var Song $episode */ /** @var Song $episode */
$episode = Song::factory()->asEpisode()->create(); $episode = Song::factory()->asEpisode()->create();
@ -170,7 +179,8 @@ class PodcastServiceTest extends TestCase
self::assertSame(123, $subscription->state->progresses[$episode->id]); self::assertSame(123, $subscription->state->progresses[$episode->id]);
} }
public function testGetStreamableUrl(): void #[Test]
public function getStreamableUrl(): void
{ {
$mock = new MockHandler([ $mock = new MockHandler([
new Response(200, ['Access-Control-Allow-Origin' => '*']), new Response(200, ['Access-Control-Allow-Origin' => '*']),
@ -185,7 +195,8 @@ class PodcastServiceTest extends TestCase
); );
} }
public function testStreamableUrlNotAvailable(): void #[Test]
public function streamableUrlNotAvailable(): void
{ {
$mock = new MockHandler([new Response(200, [])]); $mock = new MockHandler([new Response(200, [])]);
@ -195,7 +206,8 @@ class PodcastServiceTest extends TestCase
self::assertNull($this->service->getStreamableUrl('https://example.com/episode.mp3', $client)); self::assertNull($this->service->getStreamableUrl('https://example.com/episode.mp3', $client));
} }
public function testGetStreamableUrlFollowsRedirects(): void #[Test]
public function getStreamableUrlFollowsRedirects(): void
{ {
$mock = new MockHandler([ $mock = new MockHandler([
new Response(302, ['Location' => 'https://redir.example.com/track']), new Response(302, ['Location' => 'https://redir.example.com/track']),

View file

@ -5,6 +5,7 @@ namespace Tests\Integration\Services;
use App\Models\QueueState; use App\Models\QueueState;
use App\Models\Song; use App\Models\Song;
use App\Services\QueueService; use App\Services\QueueService;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
@ -20,7 +21,8 @@ class QueueServiceTest extends TestCase
$this->service = app(QueueService::class); $this->service = app(QueueService::class);
} }
public function testGetQueueState(): void #[Test]
public function getQueueState(): void
{ {
/** @var Song $currentSong */ /** @var Song $currentSong */
$currentSong = Song::factory()->create(); $currentSong = Song::factory()->create();
@ -38,7 +40,8 @@ class QueueServiceTest extends TestCase
self::assertSame(123, $dto->playbackPosition); self::assertSame(123, $dto->playbackPosition);
} }
public function testCreateQueueState(): void #[Test]
public function createQueueState(): void
{ {
$user = create_user(); $user = create_user();
@ -56,7 +59,8 @@ class QueueServiceTest extends TestCase
self::assertSame(0, $queueState->playback_position); self::assertSame(0, $queueState->playback_position);
} }
public function testUpdateQueueState(): void #[Test]
public function updateQueueState(): void
{ {
/** @var QueueState $state */ /** @var QueueState $state */
$state = QueueState::factory()->create(); $state = QueueState::factory()->create();
@ -71,7 +75,8 @@ class QueueServiceTest extends TestCase
self::assertEquals(0, $state->playback_position); self::assertEquals(0, $state->playback_position);
} }
public function testUpdatePlaybackStatus(): void #[Test]
public function updatePlaybackStatus(): void
{ {
/** @var QueueState $state */ /** @var QueueState $state */
$state = QueueState::factory()->create(); $state = QueueState::factory()->create();

View file

@ -10,6 +10,7 @@ use App\Models\Song;
use App\Models\User; use App\Models\User;
use App\Services\SmartPlaylistService; use App\Services\SmartPlaylistService;
use Illuminate\Support\Collection; use Illuminate\Support\Collection;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
@ -26,7 +27,8 @@ class SmartPlaylistServiceTest extends TestCase
$this->service = app(SmartPlaylistService::class); $this->service = app(SmartPlaylistService::class);
} }
public function testTitleIs(): void #[Test]
public function titleIs(): void
{ {
$matches = Song::factory()->count(3)->create(['title' => 'Foo Something']); $matches = Song::factory()->count(3)->create(['title' => 'Foo Something']);
Song::factory()->count(3)->create(['title' => 'Bar Something']); Song::factory()->count(3)->create(['title' => 'Bar Something']);
@ -46,7 +48,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testTitleIsNot(): void #[Test]
public function titleIsNot(): void
{ {
$matches = Song::factory()->count(3)->create(['title' => 'Foo Something']); $matches = Song::factory()->count(3)->create(['title' => 'Foo Something']);
Song::factory()->count(3)->create(['title' => 'Bar Something']); Song::factory()->count(3)->create(['title' => 'Bar Something']);
@ -66,7 +69,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testTitleContains(): void #[Test]
public function titleContains(): void
{ {
$matches = Song::factory()->count(3)->create(['title' => 'Foo Something']); $matches = Song::factory()->count(3)->create(['title' => 'Foo Something']);
Song::factory()->count(3)->create(['title' => 'Foo Nothing']); Song::factory()->count(3)->create(['title' => 'Foo Nothing']);
@ -86,7 +90,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testTitleDoesNotContain(): void #[Test]
public function titleDoesNotContain(): void
{ {
$matches = Song::factory()->count(3)->create(['title' => 'Foo Something']); $matches = Song::factory()->count(3)->create(['title' => 'Foo Something']);
Song::factory()->count(3)->create(['title' => 'Foo Nothing']); Song::factory()->count(3)->create(['title' => 'Foo Nothing']);
@ -106,7 +111,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testTitleBeginsWith(): void #[Test]
public function titleBeginsWith(): void
{ {
$matches = Song::factory()->count(3)->create(['title' => 'Foo Something']); $matches = Song::factory()->count(3)->create(['title' => 'Foo Something']);
Song::factory()->count(3)->create(['title' => 'Bar Something']); Song::factory()->count(3)->create(['title' => 'Bar Something']);
@ -126,7 +132,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testTitleEndsWith(): void #[Test]
public function titleEndsWith(): void
{ {
$matches = Song::factory()->count(3)->create(['title' => 'Foo Something']); $matches = Song::factory()->count(3)->create(['title' => 'Foo Something']);
Song::factory()->count(3)->create(['title' => 'Foo Nothing']); Song::factory()->count(3)->create(['title' => 'Foo Nothing']);
@ -146,7 +153,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testAlbumIs(): void #[Test]
public function albumIs(): void
{ {
$albums = Album::factory()->count(2)->create(['name' => 'Foo Album']); $albums = Album::factory()->count(2)->create(['name' => 'Foo Album']);
@ -170,7 +178,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testArtistIs(): void #[Test]
public function artistIs(): void
{ {
$matches = Song::factory() $matches = Song::factory()
->count(3) ->count(3)
@ -194,7 +203,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testGenreIsOrContains(): void #[Test]
public function genreIsOrContains(): void
{ {
$matches = Song::factory()->count(3)->create(['genre' => 'Foo Genre']) $matches = Song::factory()->count(3)->create(['genre' => 'Foo Genre'])
->merge(Song::factory()->count(2)->create(['genre' => 'Bar Genre'])); ->merge(Song::factory()->count(2)->create(['genre' => 'Bar Genre']));
@ -227,7 +237,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testYearIsGreaterThan(): void #[Test]
public function yearIsGreaterThan(): void
{ {
$matches = Song::factory()->count(3)->create(['year' => 2030]) $matches = Song::factory()->count(3)->create(['year' => 2030])
->merge(Song::factory()->count(2)->create(['year' => 2022])); ->merge(Song::factory()->count(2)->create(['year' => 2022]));
@ -249,7 +260,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testYearIsLessThan(): void #[Test]
public function yearIsLessThan(): void
{ {
$matches = Song::factory()->count(3)->create(['year' => 1980]) $matches = Song::factory()->count(3)->create(['year' => 1980])
->merge(Song::factory()->count(2)->create(['year' => 1978])); ->merge(Song::factory()->count(2)->create(['year' => 1978]));
@ -271,7 +283,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testYearIsBetween(): void #[Test]
public function yearIsBetween(): void
{ {
$matches = Song::factory()->count(3)->create(['year' => 1980]) $matches = Song::factory()->count(3)->create(['year' => 1980])
->merge(Song::factory()->count(2)->create(['year' => 1978])); ->merge(Song::factory()->count(2)->create(['year' => 1978]));
@ -293,7 +306,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testPlayCountIsGreaterThan(): void #[Test]
public function playCountIsGreaterThan(): void
{ {
$user = create_user(); $user = create_user();
$matches = Song::factory()->count(2)->create(); $matches = Song::factory()->count(2)->create();
@ -330,7 +344,8 @@ class SmartPlaylistServiceTest extends TestCase
], $user); ], $user);
} }
public function testLastPlayedAtIsInLast(): void #[Test]
public function lastPlayedAtIsInLast(): void
{ {
$user = create_user(); $user = create_user();
$matches = Song::factory()->count(2)->create(); $matches = Song::factory()->count(2)->create();
@ -368,7 +383,8 @@ class SmartPlaylistServiceTest extends TestCase
], $user); ], $user);
} }
public function testLastPlayedNotInLast(): void #[Test]
public function lastPlayedNotInLast(): void
{ {
$user = create_user(); $user = create_user();
$matches = Song::factory()->count(2)->create(); $matches = Song::factory()->count(2)->create();
@ -406,7 +422,8 @@ class SmartPlaylistServiceTest extends TestCase
], $user); ], $user);
} }
public function testLastPlayedIs(): void #[Test]
public function lastPlayedIs(): void
{ {
$user = create_user(); $user = create_user();
$matches = Song::factory()->count(2)->create(); $matches = Song::factory()->count(2)->create();
@ -444,7 +461,8 @@ class SmartPlaylistServiceTest extends TestCase
], $user); ], $user);
} }
public function testLengthIsGreaterThan(): void #[Test]
public function lengthIsGreaterThan(): void
{ {
$matches = Song::factory()->count(3)->create(['length' => 300]) $matches = Song::factory()->count(3)->create(['length' => 300])
->merge(Song::factory()->count(2)->create(['length' => 200])); ->merge(Song::factory()->count(2)->create(['length' => 200]));
@ -466,7 +484,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testLengthIsInBetween(): void #[Test]
public function lengthIsInBetween(): void
{ {
$matches = Song::factory()->count(3)->create(['length' => 300]) $matches = Song::factory()->count(3)->create(['length' => 300])
->merge(Song::factory()->count(2)->create(['length' => 200])); ->merge(Song::factory()->count(2)->create(['length' => 200]));
@ -488,7 +507,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testDateAddedInLast(): void #[Test]
public function dateAddedInLast(): void
{ {
$matches = Song::factory()->count(3)->create(['created_at' => now()->subDays(2)]) $matches = Song::factory()->count(3)->create(['created_at' => now()->subDays(2)])
->merge(Song::factory()->count(2)->create(['created_at' => now()->subDay()])) ->merge(Song::factory()->count(2)->create(['created_at' => now()->subDay()]))
@ -511,7 +531,8 @@ class SmartPlaylistServiceTest extends TestCase
]); ]);
} }
public function testDateAddedNotInLast(): void #[Test]
public function dateAddedNotInLast(): void
{ {
$matches = Song::factory()->count(3)->create(['created_at' => now()->subDays(4)]) $matches = Song::factory()->count(3)->create(['created_at' => now()->subDays(4)])
->merge(Song::factory()->count(2)->create(['created_at' => now()->subDays(5)])) ->merge(Song::factory()->count(2)->create(['created_at' => now()->subDays(5)]))

View file

@ -8,6 +8,7 @@ use App\Models\Setting;
use App\Services\SongStorages\LocalStorage; use App\Services\SongStorages\LocalStorage;
use Illuminate\Http\UploadedFile; use Illuminate\Http\UploadedFile;
use Mockery; use Mockery;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
@ -24,7 +25,8 @@ class LocalStorageTest extends TestCase
$this->service = app(LocalStorage::class); $this->service = app(LocalStorage::class);
} }
public function testStoreUploadedFileWithMediaPathNotSet(): void #[Test]
public function storeUploadedFileWithMediaPathNotSet(): void
{ {
Setting::set('media_path', ''); Setting::set('media_path', '');
@ -32,7 +34,8 @@ class LocalStorageTest extends TestCase
$this->service->storeUploadedFile(Mockery::mock(UploadedFile::class), create_user()); $this->service->storeUploadedFile(Mockery::mock(UploadedFile::class), create_user());
} }
public function testStoreUploadedFileFails(): void #[Test]
public function storeUploadedFileFails(): void
{ {
Setting::set('media_path', public_path('sandbox/media')); Setting::set('media_path', public_path('sandbox/media'));
@ -40,7 +43,8 @@ class LocalStorageTest extends TestCase
$this->service->storeUploadedFile(UploadedFile::fake()->create('fake.mp3'), create_user()); $this->service->storeUploadedFile(UploadedFile::fake()->create('fake.mp3'), create_user());
} }
public function testStoreUploadedFile(): void #[Test]
public function storeUploadedFile(): void
{ {
Setting::set('media_path', public_path('sandbox/media')); Setting::set('media_path', public_path('sandbox/media'));
$user = create_user(); $user = create_user();
@ -51,7 +55,8 @@ class LocalStorageTest extends TestCase
self::assertSame(public_path("sandbox/media/__KOEL_UPLOADS_\${$user->id}__/full.mp3"), $song->path); self::assertSame(public_path("sandbox/media/__KOEL_UPLOADS_\${$user->id}__/full.mp3"), $song->path);
} }
public function testStoringWithVisibilityPreference(): void #[Test]
public function storingWithVisibilityPreference(): void
{ {
$user = create_user(); $user = create_user();
$user->preferences->makeUploadsPublic = true; $user->preferences->makeUploadsPublic = true;

View file

@ -16,13 +16,16 @@ use App\Services\Streamer\Streamer;
use Exception; use Exception;
use Illuminate\Support\Facades\File; use Illuminate\Support\Facades\File;
use Illuminate\Support\Facades\Http; use Illuminate\Support\Facades\Http;
use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\test_path; use function Tests\test_path;
class StreamerTest extends TestCase class StreamerTest extends TestCase
{ {
public function testResolveAdapters(): void #[Test]
public function resolveAdapters(): void
{ {
// prevent real HTTP calls from being made e.g. from DropboxStorage // prevent real HTTP calls from being made e.g. from DropboxStorage
Http::fake(); Http::fake();
@ -53,7 +56,8 @@ class StreamerTest extends TestCase
}); });
} }
public function testResolveTranscodingAdapter(): void #[Test]
public function resolveTranscodingAdapter(): void
{ {
config(['koel.streaming.transcode_flac' => true]); config(['koel.streaming.transcode_flac' => true]);
@ -66,7 +70,8 @@ class StreamerTest extends TestCase
config(['koel.streaming.transcode_flac' => false]); config(['koel.streaming.transcode_flac' => false]);
} }
public function testForceTranscodingAdapter(): void #[Test]
public function forceTranscodingAdapter(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->make(['path' => test_path('songs/blank.mp3')]); $song = Song::factory()->make(['path' => test_path('songs/blank.mp3')]);
@ -87,8 +92,9 @@ class StreamerTest extends TestCase
]; ];
} }
/** @dataProvider provideStreamConfigData */ #[DataProvider('provideStreamConfigData')]
public function testResolveLocalAdapter(?string $config, string $expectedClass): void #[Test]
public function resolveLocalAdapter(?string $config, string $expectedClass): void
{ {
config(['koel.streaming.method' => $config]); config(['koel.streaming.method' => $config]);
@ -100,7 +106,8 @@ class StreamerTest extends TestCase
config(['koel.streaming.method' => null]); config(['koel.streaming.method' => null]);
} }
public function testResolvePodcastAdapter(): void #[Test]
public function resolvePodcastAdapter(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->asEpisode()->create(); $song = Song::factory()->asEpisode()->create();

View file

@ -5,6 +5,7 @@ namespace Tests\Integration\Services;
use App\Services\TokenManager; use App\Services\TokenManager;
use Illuminate\Support\Facades\Cache; use Illuminate\Support\Facades\Cache;
use Laravel\Sanctum\PersonalAccessToken; use Laravel\Sanctum\PersonalAccessToken;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
@ -20,14 +21,16 @@ class TokenManagerTest extends TestCase
$this->tokenManager = app(TokenManager::class); $this->tokenManager = app(TokenManager::class);
} }
public function testCreateTokenWithAllAbilities(): void #[Test]
public function createTokenWithAllAbilities(): void
{ {
$token = $this->tokenManager->createToken(create_user()); $token = $this->tokenManager->createToken(create_user());
self::assertTrue($token->accessToken->can('*')); self::assertTrue($token->accessToken->can('*'));
} }
public function testCreateTokenWithSpecificAbilities(): void #[Test]
public function createTokenWithSpecificAbilities(): void
{ {
$token = $this->tokenManager->createToken(create_user(), ['audio']); $token = $this->tokenManager->createToken(create_user(), ['audio']);
@ -36,7 +39,8 @@ class TokenManagerTest extends TestCase
self::assertFalse($token->accessToken->can('*')); self::assertFalse($token->accessToken->can('*'));
} }
public function testCreateCompositionToken(): void #[Test]
public function createCompositionToken(): void
{ {
$token = $this->tokenManager->createCompositeToken(create_user()); $token = $this->tokenManager->createCompositeToken(create_user());
@ -50,7 +54,8 @@ class TokenManagerTest extends TestCase
self::assertTrue($audioTokenInstance->is(PersonalAccessToken::findToken($cachedAudioToken))); self::assertTrue($audioTokenInstance->is(PersonalAccessToken::findToken($cachedAudioToken)));
} }
public function testDeleteCompositionToken(): void #[Test]
public function deleteCompositionToken(): void
{ {
$token = $this->tokenManager->createCompositeToken(create_user()); $token = $this->tokenManager->createCompositeToken(create_user());
@ -61,7 +66,8 @@ class TokenManagerTest extends TestCase
self::assertNull(Cache::get("app.composite-tokens.$token->apiToken")); self::assertNull(Cache::get("app.composite-tokens.$token->apiToken"));
} }
public function testDestroyTokens(): void #[Test]
public function destroyTokens(): void
{ {
$user = create_user(); $user = create_user();
$user->createToken('foo'); $user->createToken('foo');
@ -74,7 +80,8 @@ class TokenManagerTest extends TestCase
self::assertSame(0, $user->tokens()->count()); self::assertSame(0, $user->tokens()->count());
} }
public function testDeleteTokenByPlainTextToken(): void #[Test]
public function deleteTokenByPlainTextToken(): void
{ {
$token = $this->tokenManager->createToken(create_user()); $token = $this->tokenManager->createToken(create_user());
self::assertModelExists($token->accessToken); self::assertModelExists($token->accessToken);
@ -84,7 +91,8 @@ class TokenManagerTest extends TestCase
self::assertModelMissing($token->accessToken); self::assertModelMissing($token->accessToken);
} }
public function testGetUserFromPlainTextToken(): void #[Test]
public function getUserFromPlainTextToken(): void
{ {
$user = create_user(); $user = create_user();
$token = $this->tokenManager->createToken($user); $token = $this->tokenManager->createToken($user);
@ -92,7 +100,8 @@ class TokenManagerTest extends TestCase
self::assertTrue($user->is($this->tokenManager->getUserFromPlainTextToken($token->plainTextToken))); self::assertTrue($user->is($this->tokenManager->getUserFromPlainTextToken($token->plainTextToken)));
} }
public function testReplaceApiToken(): void #[Test]
public function replaceApiToken(): void
{ {
$oldToken = $this->tokenManager->createToken(create_user()); $oldToken = $this->tokenManager->createToken(create_user());
$newToken = $this->tokenManager->refreshApiToken($oldToken->plainTextToken); $newToken = $this->tokenManager->refreshApiToken($oldToken->plainTextToken);

View file

@ -9,6 +9,7 @@ use App\Services\UserInvitationService;
use Illuminate\Support\Facades\Hash; use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Facades\Mail; use Illuminate\Support\Facades\Mail;
use Illuminate\Support\Str; use Illuminate\Support\Str;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
@ -24,7 +25,8 @@ class UserInvitationServiceTest extends TestCase
$this->service = app(UserInvitationService::class); $this->service = app(UserInvitationService::class);
} }
public function testInvite(): void #[Test]
public function invite(): void
{ {
Mail::fake(); Mail::fake();
@ -45,7 +47,8 @@ class UserInvitationServiceTest extends TestCase
Mail::assertQueued(UserInvite::class, 2); Mail::assertQueued(UserInvite::class, 2);
} }
public function testGetUserProspectByToken(): void #[Test]
public function getUserProspectByToken(): void
{ {
$token = Str::uuid()->toString(); $token = Str::uuid()->toString();
$user = create_admin(); $user = create_admin();
@ -58,13 +61,15 @@ class UserInvitationServiceTest extends TestCase
self::assertTrue($this->service->getUserProspectByToken($token)->is($prospect)); self::assertTrue($this->service->getUserProspectByToken($token)->is($prospect));
} }
public function testGetUserProspectByTokenThrowsIfTokenNotFound(): void #[Test]
public function getUserProspectByTokenThrowsIfTokenNotFound(): void
{ {
$this->expectException(InvitationNotFoundException::class); $this->expectException(InvitationNotFoundException::class);
$this->service->getUserProspectByToken(Str::uuid()->toString()); $this->service->getUserProspectByToken(Str::uuid()->toString());
} }
public function testRevokeByEmail(): void #[Test]
public function revokeByEmail(): void
{ {
$user = create_admin(); $user = create_admin();
@ -79,7 +84,8 @@ class UserInvitationServiceTest extends TestCase
self::assertModelMissing($prospect); self::assertModelMissing($prospect);
} }
public function testAccept(): void #[Test]
public function accept(): void
{ {
$token = Str::uuid()->toString(); $token = Str::uuid()->toString();
$user = create_admin(); $user = create_admin();

View file

@ -6,6 +6,7 @@ use App\Exceptions\KoelPlusRequiredException;
use App\Exceptions\UserProspectUpdateDeniedException; use App\Exceptions\UserProspectUpdateDeniedException;
use App\Services\UserService; use App\Services\UserService;
use Illuminate\Support\Facades\Hash; use Illuminate\Support\Facades\Hash;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_admin; use function Tests\create_admin;
@ -25,7 +26,8 @@ class UserServiceTest extends TestCase
$this->service = app(UserService::class); $this->service = app(UserService::class);
} }
public function testCreateUser(): void #[Test]
public function createUser(): void
{ {
$user = $this->service->createUser( $user = $this->service->createUser(
name: 'Bruce Dickinson', name: 'Bruce Dickinson',
@ -41,7 +43,8 @@ class UserServiceTest extends TestCase
self::assertFileExists(user_avatar_path($user->getRawOriginal('avatar'))); self::assertFileExists(user_avatar_path($user->getRawOriginal('avatar')));
} }
public function testCreateUserWithEmptyAvatarHasGravatar(): void #[Test]
public function createUserWithEmptyAvatarHasGravatar(): void
{ {
$user = $this->service->createUser( $user = $this->service->createUser(
name: 'Bruce Dickinson', name: 'Bruce Dickinson',
@ -56,7 +59,8 @@ class UserServiceTest extends TestCase
self::assertStringStartsWith('https://www.gravatar.com/avatar/', $user->avatar); self::assertStringStartsWith('https://www.gravatar.com/avatar/', $user->avatar);
} }
public function testCreateUserWithNoPassword(): void #[Test]
public function createUserWithNoPassword(): void
{ {
$user = $this->service->createUser( $user = $this->service->createUser(
name: 'Bruce Dickinson', name: 'Bruce Dickinson',
@ -69,7 +73,8 @@ class UserServiceTest extends TestCase
self::assertEmpty($user->password); self::assertEmpty($user->password);
} }
public function testCreateSSOUserRequiresKoelPlus(): void #[Test]
public function createSSOUserRequiresKoelPlus(): void
{ {
$this->expectException(KoelPlusRequiredException::class); $this->expectException(KoelPlusRequiredException::class);
@ -82,7 +87,8 @@ class UserServiceTest extends TestCase
); );
} }
public function testUpdateUser(): void #[Test]
public function updateUser(): void
{ {
$user = create_user(); $user = create_user();
@ -104,7 +110,8 @@ class UserServiceTest extends TestCase
self::assertFileExists(user_avatar_path($user->getRawOriginal('avatar'))); self::assertFileExists(user_avatar_path($user->getRawOriginal('avatar')));
} }
public function testUpdateUserWithoutSettingPasswordOrAdminStatus(): void #[Test]
public function updateUserWithoutSettingPasswordOrAdminStatus(): void
{ {
$user = create_admin(['password' => Hash::make('TheTrooper')]); $user = create_admin(['password' => Hash::make('TheTrooper')]);
@ -122,7 +129,8 @@ class UserServiceTest extends TestCase
self::assertTrue($user->is_admin); self::assertTrue($user->is_admin);
} }
public function testUpdateProspectUserIsNotAllowed(): void #[Test]
public function updateProspectUserIsNotAllowed(): void
{ {
$this->expectException(UserProspectUpdateDeniedException::class); $this->expectException(UserProspectUpdateDeniedException::class);

View file

@ -8,6 +8,7 @@ use App\Models\Song;
use App\Services\YouTubeService; use App\Services\YouTubeService;
use Illuminate\Support\Facades\Cache; use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\File; use Illuminate\Support\Facades\File;
use PHPUnit\Framework\Attributes\Test;
use Saloon\Http\Faking\MockResponse; use Saloon\Http\Faking\MockResponse;
use Saloon\Laravel\Saloon; use Saloon\Laravel\Saloon;
use Tests\TestCase; use Tests\TestCase;
@ -25,7 +26,8 @@ class YouTubeServiceTest extends TestCase
$this->service = app(YouTubeService::class); $this->service = app(YouTubeService::class);
} }
public function testSearchVideosRelatedToSong(): void #[Test]
public function searchVideosRelatedToSong(): void
{ {
/** @var Song $song */ /** @var Song $song */
$song = Song::factory()->for(Artist::factory()->create(['name' => 'Slipknot']))->create(['title' => 'Snuff']); $song = Song::factory()->for(Artist::factory()->create(['name' => 'Slipknot']))->create(['title' => 'Snuff']);

View file

@ -6,11 +6,13 @@ use App\Models\Song;
use App\Values\Podcast\EpisodePlayable; use App\Values\Podcast\EpisodePlayable;
use Illuminate\Support\Facades\Cache; use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\Http; use Illuminate\Support\Facades\Http;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class EpisodePlayableTest extends TestCase class EpisodePlayableTest extends TestCase
{ {
public function testCreateAndRetrieved(): void #[Test]
public function createAndRetrieved(): void
{ {
Http::fake([ Http::fake([
'https://example.com/episode.mp3' => Http::response('foo'), 'https://example.com/episode.mp3' => Http::response('foo'),

View file

@ -7,13 +7,15 @@ use App\Values\TranscodeResult;
use Illuminate\Process\PendingProcess; use Illuminate\Process\PendingProcess;
use Illuminate\Support\Facades\Cache; use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\Process; use Illuminate\Support\Facades\Process;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\test_path; use function Tests\test_path;
class TranscodeResultTest extends TestCase class TranscodeResultTest extends TestCase
{ {
public function testCreateAndRetrieve(): void #[Test]
public function createAndRetrieve(): void
{ {
config(['koel.streaming.ffmpeg_path' => '/usr/bin/ffmpeg']); config(['koel.streaming.ffmpeg_path' => '/usr/bin/ffmpeg']);
Process::fake(); Process::fake();

View file

@ -2,11 +2,13 @@
namespace Tests\Unit; namespace Tests\Unit;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class ApplicationTest extends TestCase class ApplicationTest extends TestCase
{ {
public function testStaticUrlsWithoutCdnAreConstructedCorrectly(): void #[Test]
public function staticUrlsWithoutCdnAreConstructedCorrectly(): void
{ {
config(['koel.cdn.url' => '']); config(['koel.cdn.url' => '']);
@ -14,7 +16,8 @@ class ApplicationTest extends TestCase
self::assertSame('http://localhost/foo.css', static_url('/foo.css ')); self::assertSame('http://localhost/foo.css', static_url('/foo.css '));
} }
public function testStaticUrlsWithCdnAreConstructedCorrectly(): void #[Test]
public function staticUrlsWithCdnAreConstructedCorrectly(): void
{ {
config(['koel.cdn.url' => 'http://cdn.tld']); config(['koel.cdn.url' => 'http://cdn.tld']);

View file

@ -8,6 +8,7 @@ use Illuminate\Cache\Repository as Cache;
use Mockery; use Mockery;
use Mockery\LegacyMockInterface; use Mockery\LegacyMockInterface;
use Mockery\MockInterface; use Mockery\MockInterface;
use PHPUnit\Framework\Attributes\Test;
use SpotifyWebAPI\Session as SpotifySession; use SpotifyWebAPI\Session as SpotifySession;
use SpotifyWebAPI\SpotifyWebAPI; use SpotifyWebAPI\SpotifyWebAPI;
use Tests\TestCase; use Tests\TestCase;
@ -34,7 +35,8 @@ class SpotifyClientTest extends TestCase
$this->cache = Mockery::mock(Cache::class); $this->cache = Mockery::mock(Cache::class);
} }
public function testAccessTokenIsSetUponInitialization(): void #[Test]
public function accessTokenIsSetUponInitialization(): void
{ {
$this->mockSetAccessToken(); $this->mockSetAccessToken();
@ -42,7 +44,8 @@ class SpotifyClientTest extends TestCase
self::addToAssertionCount(1); self::addToAssertionCount(1);
} }
public function testAccessTokenIsRetrievedFromCacheWhenApplicable(): void #[Test]
public function accessTokenIsRetrievedFromCacheWhenApplicable(): void
{ {
$this->wrapped->shouldReceive('setOptions')->with(['return_assoc' => true]); $this->wrapped->shouldReceive('setOptions')->with(['return_assoc' => true]);
$this->cache->shouldReceive('get')->with('spotify.access_token')->andReturn('fake-access-token'); $this->cache->shouldReceive('get')->with('spotify.access_token')->andReturn('fake-access-token');
@ -54,7 +57,8 @@ class SpotifyClientTest extends TestCase
$this->client = new SpotifyClient($this->wrapped, $this->session, $this->cache); $this->client = new SpotifyClient($this->wrapped, $this->session, $this->cache);
} }
public function testCallForwarding(): void #[Test]
public function callForwarding(): void
{ {
$this->mockSetAccessToken(); $this->mockSetAccessToken();
$this->wrapped->shouldReceive('search')->with('foo', 'track')->andReturn('bar'); $this->wrapped->shouldReceive('search')->with('foo', 'track')->andReturn('bar');
@ -64,7 +68,8 @@ class SpotifyClientTest extends TestCase
self::assertSame('bar', $this->client->search('foo', 'track')); self::assertSame('bar', $this->client->search('foo', 'track'));
} }
public function testCallForwardingThrowsIfIntegrationIsDisabled(): void #[Test]
public function callForwardingThrowsIfIntegrationIsDisabled(): void
{ {
config([ config([
'koel.spotify.client_id' => null, 'koel.spotify.client_id' => null,

View file

@ -8,6 +8,7 @@ use Illuminate\Routing\UrlGenerator;
use Mockery; use Mockery;
use Mockery\LegacyMockInterface; use Mockery\LegacyMockInterface;
use Mockery\MockInterface; use Mockery\MockInterface;
use PHPUnit\Framework\Attributes\Test;
use Symfony\Component\HttpFoundation\Response; use Symfony\Component\HttpFoundation\Response;
use Tests\TestCase; use Tests\TestCase;
@ -24,7 +25,8 @@ class ForceHttpsTest extends TestCase
$this->middleware = new ForceHttps($this->url); $this->middleware = new ForceHttps($this->url);
} }
public function testHandle(): void #[Test]
public function handle(): void
{ {
config(['koel.force_https' => true]); config(['koel.force_https' => true]);
@ -47,7 +49,8 @@ class ForceHttpsTest extends TestCase
self::assertSame($response, $this->middleware->handle($request, $next)); self::assertSame($response, $this->middleware->handle($request, $next));
} }
public function testNotHandle(): void #[Test]
public function notHandle(): void
{ {
config(['koel.force_https' => false]); config(['koel.force_https' => false]);

View file

@ -6,13 +6,15 @@ use App\Jobs\ScrobbleJob;
use App\Models\Song; use App\Models\Song;
use App\Services\LastfmService; use App\Services\LastfmService;
use Mockery; use Mockery;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class ScrobbleJobTest extends TestCase class ScrobbleJobTest extends TestCase
{ {
public function testHandle(): void #[Test]
public function handle(): void
{ {
$user = create_user(); $user = create_user();

View file

@ -7,11 +7,13 @@ use App\Listeners\LoveTrackOnLastfm;
use App\Models\Interaction; use App\Models\Interaction;
use App\Services\LastfmService; use App\Services\LastfmService;
use Mockery; use Mockery;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class LoveTrackOnLastFmTest extends TestCase class LoveTrackOnLastFmTest extends TestCase
{ {
public function testHandle(): void #[Test]
public function handle(): void
{ {
/** @var Interaction $interaction */ /** @var Interaction $interaction */
$interaction = Interaction::factory()->create(); $interaction = Interaction::factory()->create();

View file

@ -7,13 +7,15 @@ use App\Listeners\MakePlaylistSongsPublic;
use App\Models\PlaylistCollaborationToken; use App\Models\PlaylistCollaborationToken;
use App\Services\PlaylistService; use App\Services\PlaylistService;
use Mockery; use Mockery;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class MakePlaylistSongsPublicTest extends TestCase class MakePlaylistSongsPublicTest extends TestCase
{ {
public function testHandle(): void #[Test]
public function handle(): void
{ {
$collaborator = create_user(); $collaborator = create_user();

View file

@ -7,13 +7,15 @@ use App\Listeners\UpdateLastfmNowPlaying;
use App\Models\Song; use App\Models\Song;
use App\Services\LastfmService; use App\Services\LastfmService;
use Mockery; use Mockery;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\create_user; use function Tests\create_user;
class UpdateLastfmNowPlayingTest extends TestCase class UpdateLastfmNowPlayingTest extends TestCase
{ {
public function testUpdateNowPlayingStatus(): void #[Test]
public function updateNowPlayingStatus(): void
{ {
$user = create_user(); $user = create_user();

View file

@ -8,6 +8,7 @@ use App\Values\ScanResult;
use App\Values\ScanResultCollection; use App\Values\ScanResultCollection;
use Carbon\Carbon; use Carbon\Carbon;
use Illuminate\Support\Facades\File; use Illuminate\Support\Facades\File;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\test_path; use function Tests\test_path;
@ -34,7 +35,8 @@ class WriteSyncLogTest extends TestCase
parent::tearDown(); parent::tearDown();
} }
public function testHandleWithLogLevelAll(): void #[Test]
public function handleWithLogLevelAll(): void
{ {
config(['koel.sync_log_level' => 'all']); config(['koel.sync_log_level' => 'all']);
@ -46,7 +48,8 @@ class WriteSyncLogTest extends TestCase
); );
} }
public function testHandleWithLogLevelError(): void #[Test]
public function handleWithLogLevelError(): void
{ {
config(['koel.sync_log_level' => 'error']); config(['koel.sync_log_level' => 'error']);

View file

@ -4,11 +4,14 @@ namespace Tests\Unit\Models;
use App\Models\Album; use App\Models\Album;
use App\Models\Artist; use App\Models\Artist;
use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
class AlbumTest extends TestCase class AlbumTest extends TestCase
{ {
public function testExistingAlbumCanBeRetrievedUsingArtistAndName(): void #[Test]
public function existingAlbumCanBeRetrievedUsingArtistAndName(): void
{ {
/** @var Album $album */ /** @var Album $album */
$album = Album::factory()->create(); $album = Album::factory()->create();
@ -16,7 +19,8 @@ class AlbumTest extends TestCase
self::assertTrue(Album::getOrCreate($album->artist, $album->name)->is($album)); self::assertTrue(Album::getOrCreate($album->artist, $album->name)->is($album));
} }
public function testNewAlbumIsAutomaticallyCreatedWithArtistAndName(): void #[Test]
public function newAlbumIsAutomaticallyCreatedWithArtistAndName(): void
{ {
/** @var Artist $artist */ /** @var Artist $artist */
$artist = Artist::factory()->create(); $artist = Artist::factory()->create();
@ -40,8 +44,9 @@ class AlbumTest extends TestCase
]; ];
} }
/** @dataProvider provideEmptyAlbumNames */ #[DataProvider('provideEmptyAlbumNames')]
public function testNewAlbumWithoutNameIsCreatedAsUnknownAlbum($name): void #[Test]
public function newAlbumWithoutNameIsCreatedAsUnknownAlbum($name): void
{ {
/** @var Artist $artist */ /** @var Artist $artist */
$artist = Artist::factory()->create(); $artist = Artist::factory()->create();

View file

@ -4,13 +4,16 @@ namespace Tests\Unit\Models;
use App\Models\Artist; use App\Models\Artist;
use Illuminate\Support\Facades\File; use Illuminate\Support\Facades\File;
use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\Attributes\Test;
use Tests\TestCase; use Tests\TestCase;
use function Tests\test_path; use function Tests\test_path;
class ArtistTest extends TestCase class ArtistTest extends TestCase
{ {
public function testExistingArtistCanBeRetrievedUsingName(): void #[Test]
public function existingArtistCanBeRetrievedUsingName(): void
{ {
/** @var Artist $artist */ /** @var Artist $artist */
$artist = Artist::factory()->create(['name' => 'Foo']); $artist = Artist::factory()->create(['name' => 'Foo']);
@ -18,7 +21,8 @@ class ArtistTest extends TestCase
self::assertTrue(Artist::getOrCreate('Foo')->is($artist)); self::assertTrue(Artist::getOrCreate('Foo')->is($artist));
} }
public function testNewArtistIsCreatedWithName(): void #[Test]
public function newArtistIsCreatedWithName(): void
{ {
self::assertNull(Artist::query()->where('name', 'Foo')->first()); self::assertNull(Artist::query()->where('name', 'Foo')->first());
self::assertSame('Foo', Artist::getOrCreate('Foo')->name); self::assertSame('Foo', Artist::getOrCreate('Foo')->name);
@ -35,13 +39,15 @@ class ArtistTest extends TestCase
]; ];
} }
/** @dataProvider provideEmptyNames */ #[DataProvider('provideEmptyNames')]
public function testGettingArtistWithEmptyNameReturnsUnknownArtist($name): void #[Test]
public function gettingArtistWithEmptyNameReturnsUnknownArtist($name): void
{ {
self::assertTrue(Artist::getOrCreate($name)->is_unknown); self::assertTrue(Artist::getOrCreate($name)->is_unknown);
} }
public function testArtistsWithNameInUtf16EncodingAreRetrievedCorrectly(): void #[Test]
public function artistsWithNameInUtf16EncodingAreRetrievedCorrectly(): void
{ {
$name = File::get(test_path('blobs/utf16')); $name = File::get(test_path('blobs/utf16'));
$artist = Artist::getOrCreate($name); $artist = Artist::getOrCreate($name);

Some files were not shown because too many files have changed in this diff Show more