Skip to content

Commit

Permalink
Merge branch 'master' of https://github.com/jikan-me/jikan-rest
Browse files Browse the repository at this point in the history
  • Loading branch information
irfan-dahir committed Mar 5, 2024
2 parents f9616f8 + 1db1d3c commit c29ce25
Show file tree
Hide file tree
Showing 7 changed files with 123 additions and 38 deletions.
2 changes: 0 additions & 2 deletions app/Http/Controllers/V4DB/ScheduleController.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,6 @@ class ScheduleController extends Controller
* operationId="getSchedules",
* tags={"schedules"},
*
* @OA\Parameter(ref="#/components/parameters/page"),
*
* @OA\Parameter(
* name="filter",
* in="query",
Expand Down
32 changes: 17 additions & 15 deletions app/Repositories/DefaultAnimeRepository.php
Original file line number Diff line number Diff line change
Expand Up @@ -5,15 +5,12 @@
use App\Anime;
use App\Contracts\AnimeRepository;
use App\Contracts\Repository;
use App\Enums\AnimeRatingEnum;
use App\Enums\AnimeScheduleFilterEnum;
use App\Enums\AnimeSeasonEnum;
use App\Enums\AnimeStatusEnum;
use App\Enums\AnimeTypeEnum;
use Illuminate\Contracts\Database\Query\Builder as EloquentBuilder;
use Illuminate\Database\Eloquent\Collection;
use Illuminate\Support\Carbon;
use Jikan\Helper\Constants;
use Laravel\Scout\Builder as ScoutBuilder;

/**
Expand Down Expand Up @@ -120,44 +117,49 @@ public function getAiredBetween(
?string $premiered = null
): EloquentBuilder
{
/** @noinspection PhpParamsInspection */
$queryable = $this->queryable(true);

$airedFilter = ["aired.from" => [
$airedFilter = ['aired.from' => [
'$gte' => $from->toAtomString(),
'$lte' => $to->modify("last day of this month")->toAtomString()
'$lte' => $to->modify('last day of this month')->toAtomString()
]];

$finalFilter = [];

// if the premiered parameter for the filter is not null, look for those items which have a premiered attribute set,
// and equals to the parameter value, OR look for those items which doesn't have premired attribute set,
// they don't have a garbled aired string and their aired.from date is within the from-to parameters range
// they don't have a garbled aired string and their aired.from date is within the from-to parameters range.
// Additionally, we want to include all those items which are carry overs from previous seasons.
if ($premiered !== null) {
$finalFilter['$or'] = [
["premiered" => $premiered],
['premiered' => $premiered],
[
"premiered" => null,
"aired.string" => [
'$not' => ['$regex' => "{$from->year} to ?"]
'premiered' => null,
'aired.string' => [
'$nin' => ["{$from->year} to ?"]
],
...$airedFilter
],
// this condition will include "continuing" items from previous seasons
[
'aired.from' => ['$lte' => $from->toAtomString()],
'airing' => true
]
];
} else {
$finalFilter = array_merge($finalFilter, $airedFilter);
$finalFilter["aired.string"] = [
'$not' => ['$regex' => "{$from->year} to ?"]
$finalFilter['aired.string'] = [
'$nin' => ["{$from->year} to ?"]
];
}

if (!is_null($type)) {
$finalFilter["type"] = $type->label;
$finalFilter['type'] = $type->label;
}

$queryable = $queryable->whereRaw($finalFilter);

return $queryable->orderBy("members", "desc");
return $queryable->orderBy('members', 'desc');
}

public function getUpcomingSeasonItems(
Expand Down
2 changes: 1 addition & 1 deletion app/Support/CachedData.php
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ public function isExpired(): bool

$expiry = $this->expiry();

return time() > $expiry;
return Carbon::now()->unix() > $expiry;
}

public function toArray(): array
Expand Down
3 changes: 2 additions & 1 deletion app/Support/RepositoryQueryBase.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
namespace App\Support;
use Laravel\Scout\Builder as ScoutBuilder;
use Illuminate\Contracts\Database\Query\Builder;
use Jenssegers\Mongodb\Eloquent\Builder as MongoDbBuilder;

class RepositoryQueryBase
{
Expand All @@ -15,7 +16,7 @@ public function __construct(
{
}

protected function queryable(bool $createNew = false): Builder
protected function queryable(bool $createNew = false): Builder|MongoDbBuilder
{
if ($createNew) {
$callback = $this->getQueryable;
Expand Down
5 changes: 1 addition & 4 deletions storage/api-docs/api-docs.json
Original file line number Diff line number Diff line change
Expand Up @@ -2283,9 +2283,6 @@
],
"operationId": "getSchedules",
"parameters": [
{
"$ref": "#/components/parameters/page"
},
{
"name": "filter",
"in": "query",
Expand Down Expand Up @@ -9104,4 +9101,4 @@
"description": "About",
"url": "https://jikan.moe"
}
}
}
89 changes: 88 additions & 1 deletion tests/Integration/SeasonControllerTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ public function testShouldFilterOutAnimeWithGarbledAiredString()
$state = $f->serializeStateDefinition([
"aired" => new CarbonDateRange($carbonStartDate, null)
]);
$state["aired"]["string"] = "Jan 1, 2024 to ?";
$state["aired"]["string"] = "2024 to ?";
$state["premiered"] = null;
$state["status"] = "Not yet aired";
$state["airing"] = false;
Expand All @@ -49,4 +49,91 @@ public function testShouldFilterOutAnimeWithGarbledAiredString()
$this->assertIsArray($content["data"]);
$this->assertCount(1, $content["data"]);
}

public function testShouldNotFilterOutFutureAiringDates()
{
Carbon::setTestNow(Carbon::parse("2024-01-11"));
// an item in the future airing
$f = Anime::factory(1);
$startDate = "2024-02-24";
$carbonStartDate = Carbon::parse($startDate);
$state = $f->serializeStateDefinition([
"aired" => new CarbonDateRange($carbonStartDate, null)
]);
$state["aired"]["string"] = "Feb 24, 2024 to ?";
$state["premiered"] = null;
$state["status"] = "Not yet aired";
$state["airing"] = false;
$f->create($state);

// the "garbled" wrong item
$f = Anime::factory(1);
$startDate = "2024-01-01";
$carbonStartDate = Carbon::parse($startDate);
$state = $f->serializeStateDefinition([
"aired" => new CarbonDateRange($carbonStartDate, null)
]);
$state["aired"]["string"] = "2024 to ?";
$state["premiered"] = null;
$state["status"] = "Not yet aired";
$state["airing"] = false;
$f->create($state);

// the absolutely correct item
$f = Anime::factory(1);
$state = $f->serializeStateDefinition([
"aired" => new CarbonDateRange(Carbon::parse("2024-01-10"), Carbon::parse("2024-02-15"))
]);
$state["premiered"] = "Winter 2024";
$state["status"] = "Currently Airing";
$state["airing"] = true;
$f->create($state);

$content = $this->getJsonResponse([], "/v4/seasons/2024/winter");
$this->seeStatusCode(200);
$this->assertIsArray($content["data"]);
$this->assertCount(2, $content["data"]);
}

public function testShouldNotFilterOutContinuingItemsFromPreviousSeasons()
{
Carbon::setTestNow(Carbon::parse("2024-01-11"));
// an item in the future airing
$f = Anime::factory(1);
$startDate = "2024-02-24";
$carbonStartDate = Carbon::parse($startDate);
$state = $f->serializeStateDefinition([
"aired" => new CarbonDateRange($carbonStartDate, null)
]);
$state["aired"]["string"] = "Feb 24, 2024 to ?";
$state["premiered"] = null;
$state["status"] = "Not yet aired";
$state["airing"] = false;
$f->create($state);

// the absolutely correct item
$f = Anime::factory(1);
$state = $f->serializeStateDefinition([
"aired" => new CarbonDateRange(Carbon::parse("2024-01-10"), Carbon::parse("2024-02-15"))
]);
$state["premiered"] = "Winter 2024";
$state["status"] = "Currently Airing";
$state["airing"] = true;
$f->create($state);

// the continuing item
$f = Anime::factory(1);
$state = $f->serializeStateDefinition([
"aired" => new CarbonDateRange(Carbon::parse("2023-10-10"), null)
]);
$state["premiered"] = "Fall 2023";
$state["status"] = "Currently Airing";
$state["airing"] = true;
$f->create($state);

$content = $this->getJsonResponse([], "/v4/seasons/2024/winter");
$this->seeStatusCode(200);
$this->assertIsArray($content["data"]);
$this->assertCount(3, $content["data"]);
}
}
28 changes: 14 additions & 14 deletions tests/Unit/DefaultCachedScraperServiceTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ private function makeCtorArgMocks(int $repositoryWhereCallCount = 1): array
public function testIfFindListReturnsNotExpiredItems()
{
$testRequestHash = $this->requestHash();
$now = Carbon::now();
$now = Carbon::createFromDate(2022, 1, 11, "UTC")->addHours(8)->addMinutes(12);
Carbon::setTestNow($now);
// the cached data in the database
// this should be an array of arrays as builder->get() returns multiple items
Expand All @@ -76,14 +76,14 @@ public function testIfFindListReturnsNotExpiredItems()
public function testIfFindListUpdatesCacheIfItemsExpired()
{
$testRequestHash = $this->requestHash();
$now = Carbon::now();
$now = Carbon::createFromDate(2022, 1, 11, "UTC")->addHours(8)->addMinutes(12);
Carbon::setTestNow($now);

// the cached data in the database
// this should be an array of arrays as builder->get() returns multiple items
$dummyResults = collect([[
"request_hash" => $testRequestHash,
"modifiedAt" => new UTCDateTime($now->sub("2 days")->getPreciseTimestamp(3)),
"modifiedAt" => new UTCDateTime($now->copy()->subDays(2)->getPreciseTimestamp(3)),
"results" => [
["dummy" => "dummy1"],
["dummy" => "dummy2"]
Expand Down Expand Up @@ -128,7 +128,7 @@ function () use (&$updatedData) {
public function testIfFindListUpdatesCacheIfCacheIsEmpty()
{
$testRequestHash = $this->requestHash();
$now = Carbon::now();
$now = Carbon::createFromDate(2022, 1, 11, "UTC")->addHours(8)->addMinutes(12);
Carbon::setTestNow($now);

// the data returned by the scraper
Expand Down Expand Up @@ -175,7 +175,7 @@ public function testIfFindReturnsNotExpiredItems()
{
$malId = 1;
$testRequestHash = $this->requestHash();
$now = Carbon::now();
$now = Carbon::createFromDate(2022, 1, 11, "UTC")->addHours(8)->addMinutes(12);
Carbon::setTestNow($now);
$mockModel = Anime::factory()->makeOne([
"mal_id" => $malId,
Expand All @@ -197,7 +197,7 @@ public function testIfFindScrapesNotFoundKey()
{
$malId = 1;
$testRequestHash = $this->requestHash();
$now = Carbon::now();
$now = Carbon::createFromDate(2022, 1, 11, "UTC")->addHours(8)->addMinutes(12);
Carbon::setTestNow($now);
$mockModel = Anime::factory()->makeOne([
"mal_id" => $malId,
Expand All @@ -224,11 +224,11 @@ public function testIfFindUpdatesExpiredDbItem()
{
$malId = 1;
$testRequestHash = $this->requestHash();
$now = Carbon::now();
$now = Carbon::createFromDate(2022, 1, 11, "UTC")->addHours(8)->addMinutes(12);
$mockModel = Anime::factory()->makeOne([
"mal_id" => $malId,
"modifiedAt" => new UTCDateTime($now->sub("3 days")->getPreciseTimestamp(3)),
"createdAt" => new UTCDateTime($now->sub("3 days")->getPreciseTimestamp(3))
"modifiedAt" => new UTCDateTime($now->copy()->sub("3 days")->getPreciseTimestamp(3)),
"createdAt" => new UTCDateTime($now->copy()->sub("3 days")->getPreciseTimestamp(3))
]);
$now = Carbon::now();
Carbon::setTestNow($now);
Expand Down Expand Up @@ -264,7 +264,7 @@ public function testIfFindByKeyReturnsNotExpiredItems()
{
$username = "kompot";
$testRequestHash = $this->requestHash();
$now = Carbon::now();
$now = Carbon::createFromDate(2022, 1, 11, "UTC")->addHours(8)->addMinutes(12);
Carbon::setTestNow($now);
$mockModel = Profile::factory()->makeOne([
"username" => $username,
Expand All @@ -287,7 +287,7 @@ public function testIfFindByKeyScrapesNotFoundKey()
{
$username = "kompot";
$testRequestHash = $this->requestHash();
$now = Carbon::now();
$now = Carbon::createFromDate(2022, 1, 11, "UTC")->addHours(8)->addMinutes(12);
Carbon::setTestNow($now);
$mockModel = Profile::factory()->makeOne([
"username" => $username,
Expand Down Expand Up @@ -319,12 +319,12 @@ public function testIfFindByKeyUpdatesCache()
$malId = 1;
$username = "kompot";
$testRequestHash = $this->requestHash();
$now = Carbon::now();
$now = Carbon::createFromDate(2022, 1, 11, "UTC")->addHours(8)->addMinutes(12);
$mockModel = Profile::factory()->makeOne([
"mal_id" => $malId,
"username" => $username,
"modifiedAt" => new UTCDateTime($now->sub("3 days")->getPreciseTimestamp(3)),
"createdAt" => new UTCDateTime($now->sub("3 days")->getPreciseTimestamp(3))
"modifiedAt" => new UTCDateTime($now->copy()->sub("3 days")->getPreciseTimestamp(3)),
"createdAt" => new UTCDateTime($now->copy()->sub("3 days")->getPreciseTimestamp(3))
]);
$now = Carbon::now();
Carbon::setTestNow($now);
Expand Down

0 comments on commit c29ce25

Please sign in to comment.