Deploy Ladill Meet / deploy (push) Failing after 7s
Phases 0–18: core meetings, webinar, breakouts, team chat, live streaming, town hall, billing, and Ladill Mail calendar wiring. Co-authored-by: Cursor <cursoragent@cursor.com>
109 lines
3.7 KiB
PHP
109 lines
3.7 KiB
PHP
<?php
|
|
|
|
namespace App\Services\Meet\Calendar;
|
|
|
|
use App\Models\CalendarConnection;
|
|
use App\Models\Room;
|
|
use App\Models\User;
|
|
use App\Services\Meet\IcalService;
|
|
use Illuminate\Support\Facades\Http;
|
|
|
|
class GoogleCalendarProvider
|
|
{
|
|
public function authorizeUrl(): ?string
|
|
{
|
|
$clientId = config('meet.calendar.google.client_id');
|
|
$redirect = config('meet.calendar.google.redirect');
|
|
|
|
if (! $clientId || ! $redirect) {
|
|
return null;
|
|
}
|
|
|
|
$params = http_build_query([
|
|
'client_id' => $clientId,
|
|
'redirect_uri' => $redirect,
|
|
'response_type' => 'code',
|
|
'scope' => 'https://www.googleapis.com/auth/calendar.events',
|
|
'access_type' => 'offline',
|
|
'prompt' => 'consent',
|
|
]);
|
|
|
|
return 'https://accounts.google.com/o/oauth2/v2/auth?'.$params;
|
|
}
|
|
|
|
/**
|
|
* @return array<string, mixed>|null
|
|
*/
|
|
public function exchangeCode(string $code): ?array
|
|
{
|
|
$response = Http::asForm()->post('https://oauth2.googleapis.com/token', [
|
|
'code' => $code,
|
|
'client_id' => config('meet.calendar.google.client_id'),
|
|
'client_secret' => config('meet.calendar.google.client_secret'),
|
|
'redirect_uri' => config('meet.calendar.google.redirect'),
|
|
'grant_type' => 'authorization_code',
|
|
]);
|
|
|
|
return $response->successful() ? $response->json() : null;
|
|
}
|
|
|
|
public function createEvent(CalendarConnection $connection, Room $room, User $host): ?string
|
|
{
|
|
if (! $connection->access_token) {
|
|
return null;
|
|
}
|
|
|
|
$response = Http::withToken($connection->access_token)->post(
|
|
'https://www.googleapis.com/calendar/v3/calendars/'.urlencode($connection->calendar_id ?? 'primary').'/events',
|
|
$this->eventPayload($room, $host),
|
|
);
|
|
|
|
return $response->successful() ? $response->json('id') : null;
|
|
}
|
|
|
|
public function updateEvent(CalendarConnection $connection, Room $room, User $host): bool
|
|
{
|
|
if (! $connection->access_token || ! $room->calendar_event_id) {
|
|
return false;
|
|
}
|
|
|
|
$calendar = urlencode($connection->calendar_id ?? 'primary');
|
|
$event = urlencode($room->calendar_event_id);
|
|
|
|
return Http::withToken($connection->access_token)->put(
|
|
"https://www.googleapis.com/calendar/v3/calendars/{$calendar}/events/{$event}",
|
|
$this->eventPayload($room, $host),
|
|
)->successful();
|
|
}
|
|
|
|
public function deleteEvent(CalendarConnection $connection, Room $room): bool
|
|
{
|
|
if (! $connection->access_token || ! $room->calendar_event_id) {
|
|
return false;
|
|
}
|
|
|
|
$calendar = urlencode($connection->calendar_id ?? 'primary');
|
|
$event = urlencode($room->calendar_event_id);
|
|
|
|
return Http::withToken($connection->access_token)->delete(
|
|
"https://www.googleapis.com/calendar/v3/calendars/{$calendar}/events/{$event}",
|
|
)->successful();
|
|
}
|
|
|
|
/** @return array<string, mixed> */
|
|
protected function eventPayload(Room $room, User $host): array
|
|
{
|
|
$start = ($room->scheduled_at ?? now())->toIso8601String();
|
|
$end = ($room->scheduled_at ?? now())->addMinutes($room->duration_minutes ?? 60)->toIso8601String();
|
|
|
|
return [
|
|
'summary' => $room->title,
|
|
'description' => trim(($room->description ?? '')."\n\nJoin: ".$room->joinUrl()),
|
|
'location' => $room->joinUrl(),
|
|
'start' => ['dateTime' => $start, 'timeZone' => $room->timezone],
|
|
'end' => ['dateTime' => $end, 'timeZone' => $room->timezone],
|
|
'organizer' => ['email' => $host->email, 'displayName' => $host->name],
|
|
];
|
|
}
|
|
}
|