Skip to content

Commit

Permalink
Count legacy RF replays properly when it comes to ranking. (#519)
Browse files Browse the repository at this point in the history
  • Loading branch information
n-rook authored Jan 13, 2025
1 parent fb19187 commit 0eca112
Show file tree
Hide file tree
Showing 2 changed files with 279 additions and 0 deletions.
223 changes: 223 additions & 0 deletions project/thscoreboard/replays/migrations/0043_replay_legacy_rank.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,223 @@
# Generated by Django 4.2.4 on 2025-01-13 19:10

from django.db import migrations


class Migration(migrations.Migration):
"""Fix rank view to include RF replays."""

dependencies = [
("replays", "0042_unique_rank_view"),
]

operations = [
migrations.RunSQL(
sql="""
CREATE OR REPLACE VIEW replays_rank
AS
SELECT
row_number() over () as id,
replay,
score,
shot_id,
difficulty,
route_id,
category,
place
FROM
(
SELECT
replay,
score,
shot_id,
difficulty,
route_id,
category,
created,
rank() OVER (
PARTITION BY shot_id,
difficulty,
route_id,
category
ORDER BY
score DESC,
created,
replay
) as place
FROM
(
SELECT
replay,
score,
shot_id,
difficulty,
route_id,
category,
created,
user_id,
imported_username
FROM
(
-- Per-user bests
(
SELECT
id as replay,
score,
shot_id,
difficulty,
route_id,
category,
created,
user_id,
NULL as imported_username,
rank() OVER (
PARTITION BY shot_id,
difficulty,
route_id,
category,
user_id
ORDER BY
score DESC,
created,
id
) as per_user_place
FROM
replays_replay
WHERE
replay_type = 1 -- FULL_GAME
AND category = 1 -- STANDARD
AND user_id IS NOT NULL
)
UNION ALL
-- Per-username bests for imported, unowned Royalflare replays
(
SELECT
id as replay,
score,
shot_id,
difficulty,
route_id,
category,
created,
NULL as user_id,
imported_username,
rank() OVER (
PARTITION BY shot_id,
difficulty,
route_id,
category,
imported_username
ORDER BY
score DESC,
created,
id
) as per_user_place
FROM
replays_replay
WHERE
replay_type = 1 -- FULL_GAME
AND category = 1 -- STANDARD
AND user_id IS NULL
AND imported_username IS NOT NULL
)
)
AS replays_ranked_per_user
WHERE
per_user_place = 1
) AS top_replays_per_user
) AS top_replays
WHERE
place <= 3
ORDER BY
shot_id,
difficulty,
route_id,
category,
place DESC;
""",
reverse_sql="""
CREATE OR REPLACE VIEW replays_rank
AS
SELECT
row_number() over () as id,
replay,
score,
shot_id,
difficulty,
route_id,
category,
place
FROM
(
SELECT
replay,
score,
shot_id,
difficulty,
route_id,
category,
created,
rank() OVER (
PARTITION BY shot_id,
difficulty,
route_id,
category
ORDER BY
score DESC,
created,
replay
) as place
FROM
(
SELECT
replay,
score,
shot_id,
difficulty,
route_id,
category,
created,
user_id
FROM
(
SELECT
id as replay,
score,
shot_id,
difficulty,
route_id,
category,
created,
user_id,
rank() OVER (
PARTITION BY shot_id,
difficulty,
route_id,
category,
user_id
ORDER BY
score DESC,
created,
id
) as per_user_place
FROM
replays_replay
WHERE
replay_type = 1 -- FULL_GAME
AND category = 1 -- STANDARD
) AS replays_ranked_per_user
WHERE
per_user_place = 1
) AS top_replays_per_user
) AS top_replays
WHERE
place <= 3
ORDER BY
shot_id,
difficulty,
route_id,
category,
place DESC;
""",
)
]
56 changes: 56 additions & 0 deletions project/thscoreboard/replays/test_models.py
Original file line number Diff line number Diff line change
Expand Up @@ -231,6 +231,62 @@ def testOnlyBestRecordFromAPlayerIsRanked(self):
self.assertIsNone(replays[1].GetRank())
self.assertIsNone(replays[3].GetRank())

def testCorrectlyRanksMixOfOwnedAndLegacyReplays(self):
test_replays.CreateAsPublishedReplay(
filename="th6_extra",
user=self.user1,
imported_username=None,
score=1_000_000_000,
)
test_replays.CreateAsPublishedReplay(
filename="th6_extra",
user=None,
imported_username="user2",
score=900_000_000,
)
test_replays.CreateAsPublishedReplay(
filename="th6_extra",
user=None,
imported_username="user2",
score=800_000_000,
)
test_replays.CreateAsPublishedReplay(
filename="th6_extra",
user=None,
imported_username="user3",
score=700_000_000,
)

replays = (
models.Replay.objects.order_by("-score").select_related("rank_view").all()
)

self.assertEqual(replays[0].GetRank(), 1)
self.assertEqual(replays[1].GetRank(), 2)
self.assertIsNone(replays[2].GetRank())
self.assertEqual(replays[3].GetRank(), 3)

def testOwnedLegacyReplayRankedTogetherWithOwnedNewReplay(self):
test_replays.CreateAsPublishedReplay(
filename="th6_extra",
user=self.user1,
imported_username=None,
score=1_000_000_000,
)
test_replays.CreateAsPublishedReplay(
filename="th6_extra",
user=self.user1,
imported_username="user1",
score=900_000_000,
)

replays = (
models.Replay.objects.order_by("-score").select_related("rank_view").all()
)

self.assertEqual(replays[0].GetRank(), 1)
self.assertIsNone(replays[1].GetRank())


class ReplayTest(test_case.ReplayTestCase):
def setUp(self):
Expand Down

0 comments on commit 0eca112

Please sign in to comment.