authorize('addRestream', $episode); $validatedData = $request->validate([ 'accept_comms' => 'boolean', 'accept_tracker' => 'boolean', 'channel_id' => 'numeric|exists:App\Models\Channel,id', ]); $channel = Channel::find($validatedData['channel_id']); $this->authorize('addEpisode', $channel); foreach ($episode->channels as $c) { if ($c->id == $channel->id) { throw new \Exception('channel already exists on episode'); } } $validatedProps = $request->validate([ 'accept_comms' => 'boolean', 'accept_tracker' => 'boolean', ]); $episode->channels()->attach($channel, $validatedProps); return $episode->load('channels')->toJson(); } public function crewManage(Request $request, Episode $episode) { $this->authorize('editRestream', $episode); $validatedData = $request->validate([ 'add' => 'numeric|exists:App\Models\User,id', 'channel_id' => 'numeric|exists:App\Models\Channel,id', 'confirm' => 'nullable|numeric|exists:App\Models\EpisodeCrew,id', 'remove' => 'numeric|exists:App\Models\EpisodeCrew,id', 'role' => 'string|in:commentary,setup,tracking', 'unconfirm' => 'nullable|numeric|exists:App\Models\EpisodeCrew,id', ]); $channel = Channel::find($validatedData['channel_id']); $this->authorize('editRestream', $channel); if (isset($validatedData['add'])) { $crew = $episode->crew() ->where('user_id', '=', $validatedData['add']) ->where('role', '=', $validatedData['role']) ->first(); if (!$crew) { $add_user = User::findOrFail($validatedData['add']); $crew = new EpisodeCrew(); $crew->channel()->associate($channel); $crew->episode()->associate($episode); $crew->user()->associate($add_user); $crew->role = $validatedData['role']; } $crew->confirmed = true; $crew->save(); } if (isset($validatedData['confirm'])) { $crew = EpisodeCrew::find($validatedData['confirm']); $crew->confirmed = true; $crew->save(); } if (isset($validatedData['remove'])) { $crew = EpisodeCrew::find($validatedData['remove']); if ($crew) { $crew->delete(); } } if (isset($validatedData['unconfirm'])) { $crew = EpisodeCrew::find($validatedData['unconfirm']); $crew->confirmed = false; $crew->save(); } $user = $request->user(); if ($user->isPrivileged()) { return $episode->load(['crew', 'crew.user'])->toJson(); } else { return $episode->load([ 'crew' => function ($query) use ($user) { $query->where('confirmed', true); $query->orWhere('user_id', '=', $user->id); $query->orWhereIn('channel_id', $user->channel_crews->pluck('channel_id')); }, 'crew.user', ])->toJson(); } } public function crewSignup(Request $request, Episode $episode) { if (!$request->user()) { throw new \Exception('requires user to sign up'); } $validatedData = $request->validate([ 'as' => 'string|in:commentary,tracking', 'channel_id' => 'numeric|exists:App\Models\Channel,id', ]); $channel = $episode->channels()->find($validatedData['channel_id']); if (!$channel) { throw new \Exception('channel not found'); } $as = $validatedData['as']; if ($as == 'commentary' && !$channel->pivot->accept_comms) { throw new \Exception('channel not looking for commentary'); } if ($as == 'tracking' && !$channel->pivot->accept_tracker) { throw new \Exception('channel not looking for trackers'); } $user = $request->user(); foreach ($episode->crew as $crew) { if ($crew->user_id == $user->id && $crew->role == $as) { throw new \Exception('already signed up'); } } $episode->crew()->create([ 'channel_id' => $channel->id, 'role' => $as, 'user_id' => $user->id, ]); if ($user->isPrivileged()) { return $episode->load(['crew', 'crew.user'])->toJson(); } else { return $episode->load([ 'crew' => function ($query) use ($user) { $query->where('confirmed', true); $query->orWhere('user_id', '=', $user->id); $query->orWhereIn('channel_id', $user->channel_crews->pluck('channel_id')); }, 'crew.user', ])->toJson(); } } public function editRestream(Request $request, Episode $episode) { $this->authorize('editRestream', $episode); $validatedData = $request->validate([ 'channel_id' => 'numeric|exists:App\Models\Channel,id', ]); $channel = Channel::find($validatedData['channel_id']); $this->authorize('editRestream', $channel); $validatedChanges = $request->validate([ 'accept_comms' => 'boolean', 'accept_tracker' => 'boolean', ]); $episode->channels()->updateExistingPivot($channel, $validatedChanges); return $episode->load('channels')->toJson(); } public function removeRestream(Request $request, Episode $episode) { $this->authorize('removeRestream', $episode); $validatedData = $request->validate([ 'channel_id' => 'numeric|exists:App\Models\Channel,id', ]); $channel = Channel::find($validatedData['channel_id']); $this->authorize('removeEpisode', $channel); $episode->channels()->detach($channel); return $episode->load('channels')->toJson(); } public function search(Request $request) { $validatedData = $request->validate([ 'after' => 'nullable|date', 'before' => 'nullable|date', 'event' => 'nullable|array', 'event.*' => 'numeric', ]); $after = isset($validatedData['after']) ? $validatedData['after'] : Carbon::now(); $before = isset($validatedData['before']) ? $validatedData['before'] : Carbon::now()->add(1, 'days'); $episodes = Episode::with(['channels', 'event', 'players', 'players.user']) ->select('episodes.*') ->join('events', 'episodes.event_id', '=', 'events.id') ->where('episodes.confirmed', '=', true) ->where(DB::raw('DATE_ADD(`episodes`.`start`, INTERVAL COALESCE(`episodes`.`estimate`, 0) SECOND)'), '>=', $after) ->where('episodes.start', '<=', $before) ->where('events.visible', '=', true) ->orderBy('episodes.start') ->limit(1000); if (!empty($validatedData['event'])) { $episodes = $episodes->whereIn('episodes.event_id', $validatedData['event']); } if ($request->user() && $request->user()->isPrivileged()) { $episodes = $episodes->with(['crew', 'crew.user']); } else if ($request->user()) { $episodes = $episodes->with([ 'crew' => function ($query) use ($request) { $query->where('confirmed', true); $query->orWhere('user_id', '=', $request->user()->id); $query->orWhereIn('channel_id', $request->user()->channel_crews->pluck('channel_id')); }, 'crew.user', ]); } else { $episodes = $episodes->with([ 'crew' => function ($query) { $query->where('confirmed', true); }, 'crew.user', ]); } return $episodes->get()->toJson(); } public function single(Request $request, Episode $episode) { $this->authorize('view', $episode); return $episode->toJson(); } }