remove osu leaderboard again
This commit is contained in:
parent
9575403ea4
commit
fe83ed7660
9 changed files with 0 additions and 487 deletions
|
@ -31,6 +31,5 @@ class CronCommand extends ChainedCommand
|
||||||
StatusCheckCommand::class,
|
StatusCheckCommand::class,
|
||||||
ResyncForumStatsCommand::class,
|
ResyncForumStatsCommand::class,
|
||||||
RebuildForumCacheCommand::class,
|
RebuildForumCacheCommand::class,
|
||||||
OsuLeaderboardUpdateCommand::class,
|
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,75 +0,0 @@
|
||||||
<?php
|
|
||||||
/**
|
|
||||||
* Holds the osu-leaderboard-update command controller.
|
|
||||||
* @package Sakura
|
|
||||||
*/
|
|
||||||
|
|
||||||
namespace Sakura\Console\Command;
|
|
||||||
|
|
||||||
use Carbon\Carbon;
|
|
||||||
use CLIFramework\Command;
|
|
||||||
use Sakura\DB;
|
|
||||||
use Sakura\OsuLeaderboard;
|
|
||||||
use Sakura\User;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Connects to the osu!api and stores new data.
|
|
||||||
* @package Sakura
|
|
||||||
* @author Julian van de Groep <me@flash.moe>
|
|
||||||
*/
|
|
||||||
class OsuLeaderboardUpdateCommand extends Command
|
|
||||||
{
|
|
||||||
/**
|
|
||||||
* A quick description of this command.
|
|
||||||
* @return string.
|
|
||||||
*/
|
|
||||||
public function brief(): string
|
|
||||||
{
|
|
||||||
return 'Connects to the osu!api and stores new data.';
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Command.
|
|
||||||
*/
|
|
||||||
public function execute(): void
|
|
||||||
{
|
|
||||||
$this->getLogger()->writeln('Updating osu! leaderboard...');
|
|
||||||
|
|
||||||
$api_key = config('osu.api_key');
|
|
||||||
|
|
||||||
if ($api_key === null) {
|
|
||||||
$this->getLogger()->writeln("Your api key isn't set in the config, get one at https://osu.ppy.sh/p/api.");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
$game_modes = [
|
|
||||||
'osu!',
|
|
||||||
'osu!taiko',
|
|
||||||
'osu!catch',
|
|
||||||
'osu!mania',
|
|
||||||
];
|
|
||||||
|
|
||||||
$osulb = new OsuLeaderboard($api_key);
|
|
||||||
$start = Carbon::now();
|
|
||||||
|
|
||||||
$users = DB::table('users')
|
|
||||||
->whereNotNull('user_osu')
|
|
||||||
->get(['user_id']);
|
|
||||||
|
|
||||||
foreach ($game_modes as $mode => $name) {
|
|
||||||
$this->getLogger()->writeln(PHP_EOL . "=> {$name}");
|
|
||||||
|
|
||||||
foreach ($users as $user) {
|
|
||||||
$user = User::construct($user->user_id);
|
|
||||||
|
|
||||||
$user_display = $user->osu . ($user->username !== $user->osu ? " ({$user->username})" : '');
|
|
||||||
$this->getLogger()->writeln("==> Updating {$name} scores for {$user_display}...");
|
|
||||||
|
|
||||||
$osulb->update($user->osu, $user, $mode);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
$this->getLogger()->writeln(PHP_EOL . "Purging inactive data...");
|
|
||||||
$osulb->purge($start);
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,45 +0,0 @@
|
||||||
<?php
|
|
||||||
/**
|
|
||||||
* Holds the osu! specific stuff controller.
|
|
||||||
* @package Sakura
|
|
||||||
*/
|
|
||||||
|
|
||||||
namespace Sakura\Controllers;
|
|
||||||
|
|
||||||
use Sakura\CurrentSession;
|
|
||||||
use Sakura\DB;
|
|
||||||
use Sakura\Notification;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Notification stuff.
|
|
||||||
* @package Sakura
|
|
||||||
* @author Julian van de Groep <me@flash.moe>
|
|
||||||
*/
|
|
||||||
class OsuController extends Controller
|
|
||||||
{
|
|
||||||
private const MODES = [
|
|
||||||
'osu!standard',
|
|
||||||
'osu!taiko',
|
|
||||||
'osu!catch',
|
|
||||||
'osu!mania',
|
|
||||||
];
|
|
||||||
|
|
||||||
public function leaderboard(): string
|
|
||||||
{
|
|
||||||
return view('osu/leaderboard', ['gamemodes' => static::MODES]);
|
|
||||||
}
|
|
||||||
|
|
||||||
public function leaderboardData(): string
|
|
||||||
{
|
|
||||||
$mode = $_GET['mode'] ?? -1;
|
|
||||||
|
|
||||||
if (!array_key_exists($mode, static::MODES)) {
|
|
||||||
return $this->json(['error' => 'Invalid game mode.']);
|
|
||||||
}
|
|
||||||
|
|
||||||
return $this->json(DB::table('osu_leaderboard')
|
|
||||||
->where('osu_game_mode', $mode)
|
|
||||||
->orderBy('osu_rank')
|
|
||||||
->get());
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,111 +0,0 @@
|
||||||
<?php
|
|
||||||
/**
|
|
||||||
* Holds the osu!leaderboard backend.
|
|
||||||
* @package Sakura
|
|
||||||
*/
|
|
||||||
|
|
||||||
namespace Sakura;
|
|
||||||
|
|
||||||
use Carbon\Carbon;
|
|
||||||
use Illuminate\Database\Query\Builder;
|
|
||||||
use stdClass;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* osu!leaderboard backend.
|
|
||||||
* @package Sakura
|
|
||||||
* @author Julian van de Groep <me@flash.moe>
|
|
||||||
*/
|
|
||||||
class OsuLeaderboard
|
|
||||||
{
|
|
||||||
private const ENDPOINT = "https://osu.ppy.sh/api/";
|
|
||||||
|
|
||||||
protected $apiKey;
|
|
||||||
|
|
||||||
public function __construct(string $apiKey)
|
|
||||||
{
|
|
||||||
$this->apiKey = $apiKey;
|
|
||||||
}
|
|
||||||
|
|
||||||
public function purge(Carbon $before): void
|
|
||||||
{
|
|
||||||
DB::table('osu_leaderboard')
|
|
||||||
->where('updated_on', '<', $before)
|
|
||||||
->delete();
|
|
||||||
}
|
|
||||||
|
|
||||||
public function update($osu, User $user, int $mode = 0): void
|
|
||||||
{
|
|
||||||
// skip if the user hasn't been online for a month
|
|
||||||
if ($user->lastOnline < time() - 30 * 24 * 60 * 60) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
$osu_user = $this->apiGetUser($osu, $mode);
|
|
||||||
|
|
||||||
if (!$osu_user || $osu_user->pp_raw < 1) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
$exists = DB::table('osu_leaderboard')
|
|
||||||
->where(is_int($osu) ? 'osu_user_id' : 'osu_username', $osu)
|
|
||||||
->where('user_id', $user->id)
|
|
||||||
->where('osu_game_mode', $mode)
|
|
||||||
->count() > 1;
|
|
||||||
|
|
||||||
$data = [
|
|
||||||
'user_id' => $user->id,
|
|
||||||
'username' => $user->username,
|
|
||||||
|
|
||||||
'osu_user_id' => intval($osu_user->user_id),
|
|
||||||
'osu_username' => $osu_user->username,
|
|
||||||
|
|
||||||
'osu_game_mode' => $mode,
|
|
||||||
|
|
||||||
'osu_count_300' => intval($osu_user->count300),
|
|
||||||
'osu_count_100' => intval($osu_user->count100),
|
|
||||||
'osu_count_50' => intval($osu_user->count50),
|
|
||||||
|
|
||||||
'osu_count_ss' => intval($osu_user->count_rank_ss),
|
|
||||||
'osu_count_s' => intval($osu_user->count_rank_s),
|
|
||||||
'osu_count_a' => intval($osu_user->count_rank_a),
|
|
||||||
|
|
||||||
'osu_play_count' => intval($osu_user->playcount),
|
|
||||||
'osu_score_ranked' => intval($osu_user->ranked_score),
|
|
||||||
'osu_score_total' => intval($osu_user->total_score),
|
|
||||||
'osu_rank' => intval($osu_user->pp_rank),
|
|
||||||
|
|
||||||
'osu_country' => $osu_user->country,
|
|
||||||
'osu_rank_country' => intval($osu_user->pp_country_rank),
|
|
||||||
|
|
||||||
'osu_performance' => floatval($osu_user->pp_raw),
|
|
||||||
'osu_accuracy' => floatval($osu_user->accuracy),
|
|
||||||
'osu_level' => floatval($osu_user->level),
|
|
||||||
|
|
||||||
'updated_on' => Carbon::now(),
|
|
||||||
];
|
|
||||||
|
|
||||||
if ($exists) {
|
|
||||||
DB::table('osu_leaderboard')
|
|
||||||
->where('osu_user_id', $data->osu_user_id)
|
|
||||||
->where('user_id', $data->user_id)
|
|
||||||
->where('osu_game_mode', $data->mode)
|
|
||||||
->update($data);
|
|
||||||
} else {
|
|
||||||
DB::table('osu_leaderboard')
|
|
||||||
->insert($data);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private function apiGetUser($user, int $mode = 0): ?stdClass
|
|
||||||
{
|
|
||||||
$result = json_decode(
|
|
||||||
Net::request(static::ENDPOINT . "get_user?k={$this->apiKey}&u={$user}&m={$mode}")
|
|
||||||
);
|
|
||||||
|
|
||||||
if ($result === false || count($result) < 1) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
return $result[0];
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -221,7 +221,3 @@ check['flash.moe https'] = "flash.moe/443/https"
|
||||||
; LastFM settings
|
; LastFM settings
|
||||||
[lastfm]
|
[lastfm]
|
||||||
api_key =
|
api_key =
|
||||||
|
|
||||||
; osu! settings
|
|
||||||
[osu]
|
|
||||||
api_key =
|
|
||||||
|
|
|
@ -1,59 +0,0 @@
|
||||||
<?php
|
|
||||||
use Illuminate\Database\Migrations\Migration;
|
|
||||||
use Illuminate\Database\Schema\Blueprint;
|
|
||||||
use Sakura\DB;
|
|
||||||
|
|
||||||
class OsuLeaderboardTables extends Migration
|
|
||||||
{
|
|
||||||
/**
|
|
||||||
* Run the migrations.
|
|
||||||
* @return void
|
|
||||||
*/
|
|
||||||
public function up()
|
|
||||||
{
|
|
||||||
$schema = DB::getSchemaBuilder();
|
|
||||||
|
|
||||||
$schema->create('osu_leaderboard', function (Blueprint $table) {
|
|
||||||
$table->integer('user_id');
|
|
||||||
$table->string('username');
|
|
||||||
|
|
||||||
$table->integer('osu_user_id');
|
|
||||||
$table->string('osu_username');
|
|
||||||
|
|
||||||
$table->tinyInteger('osu_game_mode');
|
|
||||||
|
|
||||||
$table->integer('osu_count_300');
|
|
||||||
$table->integer('osu_count_100');
|
|
||||||
$table->integer('osu_count_50');
|
|
||||||
|
|
||||||
$table->integer('osu_count_ss');
|
|
||||||
$table->integer('osu_count_s');
|
|
||||||
$table->integer('osu_count_a');
|
|
||||||
|
|
||||||
$table->integer('osu_play_count');
|
|
||||||
$table->bigInteger('osu_score_ranked');
|
|
||||||
$table->bigInteger('osu_score_total');
|
|
||||||
$table->integer('osu_rank');
|
|
||||||
|
|
||||||
$table->char('osu_country', 2);
|
|
||||||
$table->integer('osu_rank_country');
|
|
||||||
|
|
||||||
$table->float('osu_performance');
|
|
||||||
$table->float('osu_accuracy');
|
|
||||||
$table->float('osu_level');
|
|
||||||
|
|
||||||
$table->timestamp('updated_on');
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Reverse the migrations.
|
|
||||||
* @return void
|
|
||||||
*/
|
|
||||||
public function down()
|
|
||||||
{
|
|
||||||
$schema = DB::getSchemaBuilder();
|
|
||||||
|
|
||||||
$schema->drop('osu_leaderboard');
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1,61 +0,0 @@
|
||||||
.osu-leaderboard {
|
|
||||||
&__container {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
}
|
|
||||||
|
|
||||||
&__ranking {
|
|
||||||
font-size: 40px;
|
|
||||||
min-width: 100px;
|
|
||||||
text-align: center;
|
|
||||||
text-shadow: 1px 1px 1px #222;
|
|
||||||
|
|
||||||
&--rank-1 {
|
|
||||||
color: #D5CEA6;
|
|
||||||
}
|
|
||||||
|
|
||||||
&--rank-2 {
|
|
||||||
color: #C8D7DA;
|
|
||||||
}
|
|
||||||
|
|
||||||
&--rank-3 {
|
|
||||||
color: #C19E67;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
&__avatar {
|
|
||||||
width: 120px;
|
|
||||||
height: 120px;
|
|
||||||
}
|
|
||||||
|
|
||||||
&__info {
|
|
||||||
padding-left: 5px;
|
|
||||||
}
|
|
||||||
|
|
||||||
&__username {
|
|
||||||
font-family: @cute-font;
|
|
||||||
font-size: 20px;
|
|
||||||
}
|
|
||||||
|
|
||||||
&__stats {
|
|
||||||
font-family: @cute-font;
|
|
||||||
font-size: 16px;
|
|
||||||
}
|
|
||||||
|
|
||||||
&__ss,
|
|
||||||
&__s,
|
|
||||||
&__a {
|
|
||||||
font-style: italic;
|
|
||||||
font-weight: bold;
|
|
||||||
text-shadow: 1px 1px .5px #222;
|
|
||||||
}
|
|
||||||
|
|
||||||
&__ss,
|
|
||||||
&__s {
|
|
||||||
color: #D5CEA6;
|
|
||||||
}
|
|
||||||
|
|
||||||
&__a {
|
|
||||||
color: #299A0B;
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -25,7 +25,6 @@
|
||||||
@import "bem/link";
|
@import "bem/link";
|
||||||
@import "bem/members";
|
@import "bem/members";
|
||||||
@import "bem/news";
|
@import "bem/news";
|
||||||
@import "bem/osu-leaderboard";
|
|
||||||
@import "bem/post";
|
@import "bem/post";
|
||||||
@import "bem/profile";
|
@import "bem/profile";
|
||||||
@import "bem/settings";
|
@import "bem/settings";
|
||||||
|
|
|
@ -1,130 +0,0 @@
|
||||||
{% extends 'master.twig' %}
|
|
||||||
|
|
||||||
{% set title = 'osu! leaderboard' %}
|
|
||||||
|
|
||||||
{% block js %}
|
|
||||||
<script>
|
|
||||||
var osuModes = {{ gamemodes|json_encode|raw }};
|
|
||||||
|
|
||||||
function yuunoOsuFetch(mode) {
|
|
||||||
var client = new Sakura.AJAX,
|
|
||||||
leaderboard = Sakura.DOM.ID('osu-lb'),
|
|
||||||
loader = Sakura.DOM.ID('osu-lb-loading');
|
|
||||||
|
|
||||||
leaderboard.style.display = 'none';
|
|
||||||
loader.style.display = null;
|
|
||||||
|
|
||||||
client.SetUrl("{{ route('osu.leaderboard.data') }}?mode=" + mode);
|
|
||||||
|
|
||||||
client.AddCallback(200, function () {
|
|
||||||
var result = client.JSON();
|
|
||||||
|
|
||||||
if (result.error) {
|
|
||||||
var diag = new Sakura.Dialogue;
|
|
||||||
diag.Title = "osu! leaderboard";
|
|
||||||
diag.Text = result.error;
|
|
||||||
diag.AddCallback(Sakura.DialogueButton.Ok, function () {
|
|
||||||
yuunoOsuSwitch(osuModes[0]);
|
|
||||||
this.Close();
|
|
||||||
});
|
|
||||||
diag.Display();
|
|
||||||
} else {
|
|
||||||
yuunoOsuBuildList(result);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
client.Start(Sakura.HTTPMethod.GET);
|
|
||||||
}
|
|
||||||
|
|
||||||
function yuunoOsuBuildList(list) {
|
|
||||||
var numberFormat = new Intl.NumberFormat(navigator.language),
|
|
||||||
leaderboard = Sakura.DOM.ID('osu-lb'),
|
|
||||||
loader = Sakura.DOM.ID('osu-lb-loading');
|
|
||||||
|
|
||||||
leaderboard.innerHTML = '';
|
|
||||||
|
|
||||||
for (var rank in list) {
|
|
||||||
var score = list[rank],
|
|
||||||
dispRank = +rank + 1,
|
|
||||||
container = Sakura.DOM.Create('div', 'osu-leaderboard__container', 'osu-lb-ranking-' + rank),
|
|
||||||
ranking = Sakura.DOM.Create('div', 'osu-leaderboard__ranking osu-leaderboard__ranking--rank-' + dispRank),
|
|
||||||
avatar = Sakura.DOM.Create('div', 'avatar avatar--border osu-leaderboard__avatar'),
|
|
||||||
info = Sakura.DOM.Create('div', 'osu-leaderboard__info'),
|
|
||||||
username = Sakura.DOM.Create('a', 'osu-leaderboard__username'),
|
|
||||||
stats = Sakura.DOM.Create('div', 'osu-leaderboard__stats'),
|
|
||||||
scores = Sakura.DOM.Create('div', 'osu-leaderboard__scores'),
|
|
||||||
level = Sakura.DOM.Create('div', 'osu-leaderboard__level');
|
|
||||||
|
|
||||||
ranking.innerText = '#' + numberFormat.format(dispRank);
|
|
||||||
Sakura.DOM.Append(container, ranking);
|
|
||||||
|
|
||||||
avatar.style.backgroundImage = "url('https://a.ppy.sh/" + score.osu_user_id + "')";
|
|
||||||
Sakura.DOM.Append(container, avatar);
|
|
||||||
|
|
||||||
username.innerText = score.osu_username + (score.osu_username !== score.username ? " (" + score.username + ")" : '');
|
|
||||||
username.href = "https://osu.ppy.sh/u/" + score.osu_user_id;
|
|
||||||
username.target = "_blank";
|
|
||||||
Sakura.DOM.Append(info, username);
|
|
||||||
|
|
||||||
stats.innerHTML = numberFormat.format(Math.round(score.osu_performance)) + "pp"
|
|
||||||
+ " #" + numberFormat.format(score.osu_rank) + " (<img src='/images/flags/" + score.osu_country.toLowerCase() + ".png' alt='" + score.osu_country + "'>"
|
|
||||||
+ " #" + numberFormat.format(score.osu_rank_country) + ")"
|
|
||||||
+ " " + numberFormat.format(Math.round(score.osu_accuracy * 100) / 100) + '%';
|
|
||||||
Sakura.DOM.Append(info, stats);
|
|
||||||
|
|
||||||
scores.innerText = "scores // ranked " + numberFormat.format(score.osu_score_ranked) + " // total " + numberFormat.format(score.osu_score_total);
|
|
||||||
Sakura.DOM.Append(info, scores);
|
|
||||||
|
|
||||||
level.innerHTML = "level "
|
|
||||||
+ numberFormat.format(Math.floor(score.osu_level))
|
|
||||||
+ " // <span class='osu-leaderboard__ss'>SS</span> "
|
|
||||||
+ numberFormat.format(score.osu_count_ss)
|
|
||||||
+ " / <span class='osu-leaderboard__s'>S</span> "
|
|
||||||
+ numberFormat.format(score.osu_count_s)
|
|
||||||
+ " / <span class='osu-leaderboard__a'>A</span> "
|
|
||||||
+ numberFormat.format(score.osu_count_a);
|
|
||||||
Sakura.DOM.Append(info, level);
|
|
||||||
|
|
||||||
Sakura.DOM.Append(container, info);
|
|
||||||
Sakura.DOM.Append(leaderboard, container);
|
|
||||||
}
|
|
||||||
|
|
||||||
loader.style.display = 'none';
|
|
||||||
leaderboard.style.display = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
function yuunoOsuReload() {
|
|
||||||
yuunoOsuFetch(osuModes.indexOf(window.location.hash.substring(1)));
|
|
||||||
}
|
|
||||||
|
|
||||||
function yuunoOsuSwitch(mode) {
|
|
||||||
window.location.hash = '#' + mode;
|
|
||||||
}
|
|
||||||
|
|
||||||
window.addEventListener("hashchange", yuunoOsuReload);
|
|
||||||
|
|
||||||
window.addEventListener("load", function () {
|
|
||||||
if (!window.location.hash.substring(1)) {
|
|
||||||
yuunoOsuSwitch(osuModes[0]);
|
|
||||||
} else {
|
|
||||||
yuunoOsuReload();
|
|
||||||
}
|
|
||||||
});
|
|
||||||
</script>
|
|
||||||
{% endblock %}
|
|
||||||
|
|
||||||
{% block content %}
|
|
||||||
<div class="content">
|
|
||||||
<div class="content__header">osu! leaderboard</div>
|
|
||||||
<div style="text-align: center">
|
|
||||||
{% for mode in gamemodes %}
|
|
||||||
<h1 onclick="yuunoOsuSwitch('{{ mode }}')" style="cursor: pointer; display: inline-block; margin: 20px 10px">{{ mode }}</h1>
|
|
||||||
{% endfor %}
|
|
||||||
</div>
|
|
||||||
<div id="osu-lb-loading" style="text-align: center; margin: 2em 0">
|
|
||||||
<h1>Loading...</h1>
|
|
||||||
<h1 class="fa fa-spinner fa-spin fa-4x"></h1>
|
|
||||||
</div>
|
|
||||||
<div id="osu-lb" style="display: none"></div>
|
|
||||||
</div>
|
|
||||||
{% endblock %}
|
|
Reference in a new issue