setClientId($clientID); $client->setClientSecret($clientSecret); $client->setRedirectUri($redirectUri); $client->addScope("email"); $client->addScope("profile"); // 4. LOGIC: Handle the authentication flow if (isset($_GET['code'])) { // A. User has been redirected back from Google with an authorization code. try { // Exchange the authorization code for an access token. $token = $client->fetchAccessTokenWithAuthCode($_GET['code']); if (isset($token['error'])) { // Handle error from Google throw new Exception('Error fetching access token: ' . $token['error_description']); } $client->setAccessToken($token['access_token']); // Get user profile information from Google. $google_oauth = new Google_Service_Oauth2($client); $google_account_info = $google_oauth->userinfo->get(); $id = $google_account_info->id; $email = $google_account_info->email; $name = $google_account_info->name; $picture = $google_account_info->picture; // B. Redirect back to the Flutter app with the user data in the URL. // We use urlencode to ensure data is passed correctly. $redirectUrl = $appRedirectScheme . '?status=success' . '&id=' . urlencode($id) . '&email=' . urlencode($email) . '&name=' . urlencode($name) . '&picture=' . urlencode($picture); header('Location: ' . $redirectUrl); exit(); } catch (Exception $e) { // C. Handle any errors and redirect back to the app with an error status. $error_message = urlencode($e->getMessage()); header('Location: ' . $appRedirectScheme . '?status=error&message=' . $error_message); exit(); } } else { // D. This is the initial request from the Flutter app. // Redirect the user to Google's OAuth 2.0 server for authentication. $authUrl = $client->createAuthUrl(); header('Location: ' . $authUrl); exit(); } ?>