Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add yearly stats to summary stats response #111

Merged
merged 7 commits into from
May 3, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 6 additions & 2 deletions src/app/Http/Controllers/StatisticsController.php
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
use App\Http\Controllers\ResponseController;
use App\Http\Resources\StatisticsResource;
use App\Models\SummaryStatsView;
use App\Models\SummaryStatsViewByYear;
use Illuminate\Database\Query\Builder;
use Illuminate\Http\JsonResponse;
use Illuminate\Http\Request;
Expand All @@ -25,10 +26,13 @@ public function index(Request $request): JsonResponse

$initialSortColumn = 'Year';

$model = new SummaryStatsView();
$month = new SummaryStatsView();
$year = new SummaryStatsViewByYear();

$data = $this->getDataByRequest($request, $model, $queryColumns, $initialSortColumn);
$monthData = $this->getDataByRequest($request, $month, $queryColumns, $initialSortColumn);
$yearData = $this->getDataByRequest($request, $year, $queryColumns, $initialSortColumn);

$data = $monthData->concat($yearData);

$resource = new StatisticsResource($data);

Expand Down
25 changes: 25 additions & 0 deletions src/app/Models/SummaryStatsViewByYear.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
<?php
namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class SummaryStatsViewByYear extends Model
{
protected $table = 'summary_stats_view_by_year';

const CREATED_AT = null;
const UPDATED_AT = null;

protected $fillable = [];

protected $casts = [
'Year' => 'integer',
'Month' => 'integer',
'ScoreTypeId' => 'integer',
'UniqueUsersPerScoreType' => 'integer',
'UniqueItemsPerScoreType' => 'integer',
'OverallUniqueUsers' => 'integer',
'OverallUniqueItems' => 'integer',
'Amount' => 'integer'
];
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
<?php

use Illuminate\Database\Migrations\Migration;
use Illuminate\Support\Facades\DB;

return new class extends Migration
{
public function up(): void
{
DB::statement('DROP VIEW IF EXISTS summary_stats_view_by_year');

DB::statement('
CREATE VIEW summary_stats_view_by_year AS
SELECT
t1.Year AS Year,
0 AS Month,
t1.ScoreTypeId AS ScoreTypeId,
t1.UniqueUsers AS UniqueUsersPerScoreType,
t1.UniqueItems AS UniqueItemsPerScoreType,
t2.UniqueUsers AS OverallUniqueUsers,
t2.UniqueItems AS OverallUniqueItems,
COALESCE(t3.NumberOfFirstRecords, 0) AS OverallItemsStarted,
t1.Amount AS Amount
FROM
(
(
(
(
SELECT
YEAR(transcribathon.Score.Timestamp) AS Year,
transcribathon.Score.ScoreTypeId AS ScoreTypeId,
COUNT(DISTINCT transcribathon.Score.UserId) AS UniqueUsers,
COUNT(DISTINCT transcribathon.Score.ItemId) AS UniqueItems,
SUM(transcribathon.Score.Amount) AS Amount
FROM
transcribathon.Score
GROUP BY
YEAR(transcribathon.Score.Timestamp),
transcribathon.Score.ScoreTypeId
)
) t1
JOIN (
SELECT
YEAR(transcribathon.Score.Timestamp) AS Year,
COUNT(DISTINCT transcribathon.Score.UserId) AS UniqueUsers,
COUNT(DISTINCT transcribathon.Score.ItemId) AS UniqueItems
FROM
transcribathon.Score
GROUP BY
YEAR(transcribathon.Score.Timestamp)
) t2 ON(
(t1.Year = t2.Year)
)
)
LEFT JOIN (
SELECT
YEAR(s.Timestamp) AS Year,
COUNT(0) AS NumberOfFirstRecords
FROM
(
transcribathon.Score s
JOIN (
SELECT
transcribathon.Score.ItemId AS ItemId,
MIN(transcribathon.Score.ScoreId) AS FirstScoreId
FROM
transcribathon.Score
GROUP BY
transcribathon.Score.ItemId
) firstRecords ON(
(
(s.ItemId = firstRecords.ItemId)
and (s.ScoreId = firstRecords.FirstScoreId)
)
)
)
GROUP BY
YEAR(s.Timestamp)
) t3 ON(
(t1.Year = t3.Year)
)
)
');
}

public function down(): void
{
DB::statement('DROP VIEW IF EXISTS summary_stats_view_by_year');
}
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
<?php

use Illuminate\Database\Migrations\Migration;
use Illuminate\Support\Facades\DB;

return new class extends Migration
{
public function up(): void
{
DB::statement("
CREATE VIEW summary_stats_view_by_year AS
SELECT
t1.Year AS Year,
0 AS Month,
t1.ScoreTypeId AS ScoreTypeId,
t1.UniqueUsers AS UniqueUsersPerScoreType,
t1.UniqueItems AS UniqueItemsPerScoreType,
t2.UniqueUsers AS OverallUniqueUsers,
t2.UniqueItems AS OverallUniqueItems,
COALESCE(t3.NumberOfFirstRecords, 0) AS OverallItemsStarted,
t1.Amount AS Amount
FROM
(
(
(
(
SELECT
strftime('%Y', Score.Timestamp) AS Year,
Score.ScoreTypeId AS ScoreTypeId,
COUNT(DISTINCT Score.UserId) AS UniqueUsers,
COUNT(DISTINCT Score.ItemId) AS UniqueItems,
SUM(Score.Amount) AS Amount
FROM
Score
GROUP BY
strftime('%Y', Score.Timestamp),
Score.ScoreTypeId
)
) t1
JOIN (
SELECT
strftime('%Y', Score.Timestamp) AS Year,
COUNT(DISTINCT Score.UserId) AS UniqueUsers,
COUNT(DISTINCT Score.ItemId) AS UniqueItems
FROM
Score
GROUP BY
strftime('%Y', Score.Timestamp)
) t2 ON(
(t1.Year = t2.Year)
)
)
LEFT JOIN (
SELECT
strftime('%Y', s.Timestamp) AS Year,
COUNT(0) AS NumberOfFirstRecords
FROM
(
Score s
JOIN (
SELECT
Score.ItemId AS ItemId,
MIN(Score.ScoreId) AS FirstScoreId
FROM
Score
GROUP BY
Score.ItemId
) firstRecords ON(
(
(s.ItemId = firstRecords.ItemId)
and (s.ScoreId = firstRecords.FirstScoreId)
)
)
)
GROUP BY
strftime('%Y', s.Timestamp)
) t3 ON(
(t1.Year = t3.Year)
)
);
");
}

public function down(): void
{
DB::statement('DROP VIEW IF EXISTS summary_stats_view_by_year');
}
};
2 changes: 1 addition & 1 deletion src/storage/api-docs/api-docs.yaml
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
openapi: 3.0.3

info:
version: 1.40.0
version: 1.41.0
title: Transcribathon Platform API v2
description: This is the documentation of the Transcribathon API v2 used by [https:transcribathon.eu](https://transcribathon.eu/).<br />
For authorization you can use the the bearer token you are provided with.
Expand Down
2 changes: 1 addition & 1 deletion src/storage/api-docs/statistics-path.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ get:
type: integer
- in: query
name: Month
description: To month of the statistics (from 1-12)
description: To month of the statistics (from 1-12). With month 0 or just it will the stats for the whole year (same as omitting month completly).
type: string
responses:
200:
Expand Down
2 changes: 1 addition & 1 deletion src/storage/api-docs/statistics-schema.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ StatisticsGetResponseSchema:
example: 2021
Month:
type: integer
description: The month of the statistics (from 1-12)
description: The month of the statistics (from 1-12). Month 0 is the statistic for the whole year.
example: 1
ScoreTypeId:
type: integer
Expand Down
33 changes: 33 additions & 0 deletions src/tests/Feature/SummaryStatsTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,28 @@ public function testGetAllMonthlyBasedStatistics(): void
'OverallUniqueItems' => 1,
'OverallItemsStarted' => 1,
'Amount' => 10
],
[
'Year' => 2021,
'Month' => 0,
'ScoreTypeId' => 2,
'UniqueUsersPerScoreType' => 2,
'UniqueItemsPerScoreType' => 2,
'OverallUniqueUsers' => 2,
'OverallUniqueItems' => 2,
'OverallItemsStarted' => 2,
'Amount' => 57
],
[
'Year' => 2022,
'Month' => 0,
'ScoreTypeId' => 3,
'UniqueUsersPerScoreType' => 1,
'UniqueItemsPerScoreType' => 1,
'OverallUniqueUsers' => 1,
'OverallUniqueItems' => 1,
'OverallItemsStarted' => 1,
'Amount' => 10
]
];

Expand Down Expand Up @@ -117,6 +139,17 @@ public function testGetStatisticsByYear(): void
'OverallUniqueItems' => 2,
'OverallItemsStarted' => 2,
'Amount' => 57
],
[
'Year' => 2021,
'Month' => 0,
'ScoreTypeId' => 2,
'UniqueUsersPerScoreType' => 2,
'UniqueItemsPerScoreType' => 2,
'OverallUniqueUsers' => 2,
'OverallUniqueItems' => 2,
'OverallItemsStarted' => 2,
'Amount' => 57
]
];

Expand Down
Loading