class LockRound extends Command
{
- /**
- * The name and signature of the console command.
- *
- * @var string
- */
- protected $signature = 'round:lock {round}';
-
- /**
- * The console command description.
- *
- * @var string
- */
- protected $description = 'Lock the round';
-
- /**
- * Execute the console command.
- *
- * @return int
- */
- public function handle()
- {
+ /**
+ * The name and signature of the console command.
+ *
+ * @var string
+ */
+ protected $signature = 'round:lock {round}';
+
+ /**
+ * The console command description.
+ *
+ * @var string
+ */
+ protected $description = 'Lock the round';
+
+ /**
+ * Execute the console command.
+ *
+ * @return int
+ */
+ public function handle()
+ {
$round = Round::findOrFail($this->argument('round'));
if ($round->locked) {
RoundChanged::dispatch($round);
- return 0;
- }
+ return 0;
+ }
}
--- /dev/null
+<?php
+
+namespace App\Console\Commands;
+
+use App\Events\TournamentChanged;
+use App\Models\Protocol;
+use App\Models\Tournament;
+use Illuminate\Console\Command;
+
+class LockTournament extends Command
+{
+ /**
+ * The name and signature of the console command.
+ *
+ * @var string
+ */
+ protected $signature = 'tournament:lock {tournament}';
+
+ /**
+ * The console command description.
+ *
+ * @var string
+ */
+ protected $description = 'Lock the tournament';
+
+ /**
+ * Execute the console command.
+ *
+ * @return int
+ */
+ public function handle()
+ {
+ $tournament = Tournament::findOrFail($this->argument('tournament'));
+
+ if ($tournament->locked) {
+ $this->line('already locked');
+ return 0;
+ }
+
+ $tournament->locked = true;
+ $tournament->save();
+
+ Protocol::tournamentLocked(
+ $tournament,
+ );
+
+ TournamentChanged::dispatch($tournament);
+
+ return 0;
+ }
+}
--- /dev/null
+<?php
+
+namespace App\Events;
+
+use App\Models\Tournament;
+use Illuminate\Broadcasting\Channel;
+use Illuminate\Broadcasting\InteractsWithSockets;
+use Illuminate\Broadcasting\PresenceChannel;
+use Illuminate\Broadcasting\PrivateChannel;
+use Illuminate\Contracts\Broadcasting\ShouldBroadcast;
+use Illuminate\Foundation\Events\Dispatchable;
+use Illuminate\Queue\SerializesModels;
+
+class TournamentChanged implements ShouldBroadcast
+{
+ use Dispatchable, InteractsWithSockets, SerializesModels;
+
+ /**
+ * Create a new event instance.
+ *
+ * @return void
+ */
+ public function __construct(Tournament $tournament)
+ {
+ $this->tournament = $tournament;
+ }
+
+ /**
+ * Get the channels the event should broadcast on.
+ *
+ * @return \Illuminate\Broadcasting\Channel|array
+ */
+ public function broadcastOn()
+ {
+ return new Channel('Tournament.'.$this->tournament->id);
+ }
+
+ public $tournament;
+
+}
ProtocolAdded::dispatch($protocol);
}
+ public static function tournamentLocked(Tournament $tournament, User $user = null) {
+ $protocol = static::create([
+ 'tournament_id' => $tournament->id,
+ 'user_id' => $user ? $user->id : null,
+ 'type' => 'tournament.lock',
+ 'details' => [
+ 'tournament' => static::tournamentMemo($tournament),
+ ],
+ ]);
+ ProtocolAdded::dispatch($protocol);
+ }
+
protected static function resultMemo(Result $result) {
return [
*/
public function addRound(User $user, Tournament $tournament)
{
- return $user->role === 'admin' || $user->isParticipant($tournament);
+ return $user->role === 'admin' || (!$tournament->locked && $user->isParticipant($tournament));
}
/**
--- /dev/null
+<?php
+
+use Illuminate\Database\Migrations\Migration;
+use Illuminate\Database\Schema\Blueprint;
+use Illuminate\Support\Facades\Schema;
+
+return new class extends Migration
+{
+ /**
+ * Run the migrations.
+ *
+ * @return void
+ */
+ public function up()
+ {
+ Schema::table('tournaments', function(Blueprint $table) {
+ $table->boolean('locked')->default(false);
+ });
+ }
+
+ /**
+ * Reverse the migrations.
+ *
+ * @return void
+ */
+ public function down()
+ {
+ Schema::table('tournaments', function(Blueprint $table) {
+ $table->dropColumn('locked');
+ });
+ }
+};
if (e.round) {
setTournament(tournament => patchRound(tournament, e.round));
}
+ })
+ .listen('TournamentChanged', e => {
+ if (e.tournament) {
+ setTournament(tournament => ({ ...tournament, ...e.tournament }));
+ }
});
return () => {
window.Echo.leave(`Tournament.${id}`);
round.results.find(r => r.user_id == user.id && r.has_finished);
export const mayAddRounds = (user, tournament) =>
- isAdmin(user) || isParticipant(user, tournament);
+ isAdmin(user) || (!tournament.locked && isParticipant(user, tournament));
export const maySetSeed = (user, tournament) =>
isAdmin(user) || isParticipant(user, tournament);