Подтвердить что ты не робот

Laravel Socialite: InvalidStateException

Я использую Laravel Socialite, чтобы добавить кнопку подключения Facebook на веб-сайте. Иногда у меня есть эта ошибка при обратном вызове:

exception 'Laravel\Socialite\Two\InvalidStateException' 
in /example/vendor/laravel/socialite/src/Two/AbstractProvider.php:161

Я не знаю, что это значит и еще ничего не нашел об этой ошибке. Реальная проблема - это случайное исключение (не понимайте, почему это происходит). Итак, что означает эта ошибка и как ее избежать?

Кажется, что это не та же проблема, что Laravel 5 geting InvalidStateException в AbstractProvider.php, в моем случае это случайное.

4b9b3361

Ответ 1

Я столкнулся с этим вопросом вчера вечером и решил его с помощью следующего решения.

Дополнительная информация о моей проблеме, у меня есть

InvalidStateException в строке AbstractProvider.php 182

в функции handleProviderCallback(), когда он перенаправляется обратно из входа в Facebook. Это похоже на вашу проблему.

Кроме того, я обнаружил, что моя проблема возникает, когда я открываю свой сайт без www. Когда я открываю свой сайт с помощью www.mysite.com - никаких проблем. Сначала я думаю, что моя проблема случайна, пока у меня нет ответа от ответа Chris Townsend на вопрос - Большое спасибо.

Решение

  • Перейдите к своему корню www, проверьте файл laravel config/session.php
  • Проверить сеанс домена cookie сеанса Конфигурация по умолчанию: 'domain' => null, Я внес изменения в 'domain' => 'mysite.com'.
  • После 'php artisan cache:clear' и 'composer dump-autoload' я могу войти без проблем из www.mysite.com и mysite.com

Обязательно удалите файлы cookie из браузера при тестировании после того, как эти изменения будут выполнены. Старые файлы cookie все еще могут создавать проблемы.

Ответ 2

Решено:

Socialite::driver('google')->stateless()->user()

Ответ 3

TL;DR

Если вам нужно прочитать заданный параметр state, возвращаемый службой третьей стороны, вы можете настроить Socialite, чтобы избежать этой проверки с помощью метода stateless:

   Socialite::driver($provider)->stateless();

Я думаю, что Socialite уже готов избежать этой проблемы.

https://github.com/laravel/socialite/blob/2.0/src/Two/AbstractProvider.php#L77

 /**
 * Indicates if the session state should be utilized.
 *
 * @var bool
 */
protected $stateless = false;

https://github.com/laravel/socialite/blob/2.0/src/Two/AbstractProvider.php#L374

/**
 * Indicates that the provider should operate as stateless.
 *
 * @return $this
 */
public function stateless()
{
    $this->stateless = true;
    return $this;
}

https://github.com/laravel/socialite/blob/2.0/src/Two/AbstractProvider.php#L222

/**
 * Determine if the current request / session has a mismatching "state".
 *
 * @return bool
 */
protected function hasInvalidState()
{
    if ($this->isStateless()) {
        return false; // <--------
    }
    $state = $this->request->getSession()->pull('state');
    return ! (strlen($state) > 0 && $this->request->input('state') === $state);
}

Например, state очень полезно передавать данные через google:

Параметр: состояние (любая строка)
Предоставляет любое состояние, которое может быть полезно для вашего после получения ответа. Авторизация Google Сервер округляет этот параметр, поэтому ваше приложение получает то же самое значение, которое он отправил. Возможное использование включает перенаправление пользователя на правильный ресурс на вашем сайте и кросс-сайт-запрос-подлог смягчение.

ref: https://developers.google.com/identity/protocols/OAuth2UserAgent#overview

Ответ 4

Также проверьте доступ в своей папке storage/framework/sessions.

В моем случае, поскольку эта папка пуста в новом проекте Laravel, она была оставлена ​​во время первоначальной фиксации в репозитории GIT. Впоследствии я создал его вручную на рабочем сервере, но, очевидно, с неправильными правами доступа, поэтому он не был доступен для записи для драйвера сеанса (если он установлен на 'file').

Ответ 5

Эта ошибка возникала только при входе в систему через мобильный интернет с помощью приложения Facebook вместо Facebook в браузере. Приложение facebook использует браузер facebook после входа в систему вместо вашего текущего браузера, поэтому не знает о предыдущем состоянии.

try {
    $socialite = Socialite::driver($provider)->user();
} catch (InvalidStateException $e) {
    $socialite = Socialite::driver($provider)->stateless()->user();
}

Ответ 6

У меня была такая же проблема, и я просто очистил кеш, чтобы решить эту проблему. Я просто запустил эту команду и снова запустил процесс.

php artisan cache:clear

Я надеюсь, что этот ответ может кому-то помочь.

Ответ 7

это решило это для меня
$request->session()->put('state',Str::random(40)); $user = Socialite::driver('github')->stateless()->user();

Ответ 8

В моем случае это было вызвано отсутствием параметров в массиве $fillable в классе User. Когда я добавил все недостающие параметры, он начал работать должным образом..

Ответ 9

Есть 2 основных "ошибки", на которые ни один из существующих ответов не адресован.

  1. Иногда InvalidStateException - красная сельдь, а истинная причина - какая-то другая ошибка. Мне понадобилось ~ 12 часов один раз, чтобы понять, что я не добавил новое поле в массив $fillable в модели.
  2. Если вы не отключите проверку состояния сеанса (поскольку другие ответы здесь, по-видимому, хотят, чтобы вы это делали, но не все захотят), $provider->user() можно вызывать только один раз на запрос, потому что внутри этой функции вызывает hasInvalidState(), которая затем удаляет запись 'state' из сеанса. Мне потребовались часы, чтобы понять, что я звонил $provider->user() несколько раз, когда я должен был вызвать его всего один раз и сохранить результат в переменной.

Ответ 10

Такое случается только тогда, когда я открываю свой интернет на мобильном телефоне и открываю диалог с помощью приложения Facebook на своем телефоне.

Думаю: Это произошло потому, что открытое приложение Facebook, чтобы получить ответ от Facebook API, заставило нас потерять некоторые куки. это стало без гражданства. Тогда я просто использую опцию, что socialite уже сделаны, чтобы избежать запроса stateless.

$user = Socialite::driver($provider)->stateless()->user();

Это сработало для меня. надеюсь, это поможет вам

Ответ 11

Если вам все еще нужна помощь, вы можете использовать мой код, он работает для меня. Вам просто нужно создать два маршрута и обновить таблицу пользователей. Не забудьте сделать пароль нулевым, так как вы не получите его от пользователей facebook Код в моем контроллере:

public function redirectToProvider()
{
    return Socialize::with('facebook')->redirect();
}

public function handleProviderCallback(User $user)
{
    $money = Socialize::with('facebook')->user();

    if(User::where('email', '=', $money->email)->first()){
    $checkUser = User::where('email', '=', $money->email)->first();
    Auth::login($checkUser);
    return redirect('home');
     } 

    $user->facebook_id = $money->getId();
    $user->name = $money->getName();
    $user->email = $money->getEmail();
    $user->avatar = $money->getAvatar();
    $user->save();

    Auth::login($user);
    return redirect('home');

}

Ответ 12

Я исправил это, просто отключив SESSION DRIVER как базу данных... драйвер файла работал отлично для меня после нескольких часов, пытаясь исправить это...

Ответ 13

У меня была похожая проблема, у меня есть

InvalidStateException in AbstractProvider.php line 182

в функции handleProviderCallback() когда он перенаправляет обратно с входа в Facebook. Кажется, это то же самое, что и ваша проблема.

Кроме того, я обнаружил, что моя проблема возникает, когда я открываю свой сайт без www. Когда я открываю свой сайт с www.mysite.com - нет проблем. Сначала я думаю, что моя проблема случайна, пока Крис Таунсенд не получил ответ на этот вопрос.

Решение

Перейдите в корневой каталог www, проверьте файл config/session.php laravel. Проверьте сеанс Session Cookie Domain. Конфигурация по умолчанию

'domain' => null,

Я внес изменения в

'domain' => 'mysite.com' 

После того, как php artisan cache:clear и composer dump-autoload, я могу без проблем войти как с www.mysite.com, так и с mysite.com

Обязательно удалите файлы cookie из браузера при тестировании после внесения этих изменений. Старые куки все еще могут создавать проблемы.

Ответ 14

Получил Решение - Обновление Ноябрь 2018

public function redirectToGoogle(Request $request)
{
    /**
     * @var GoogleProvider $googleDriver
     */
    $googleDriver = Socialite::driver("google");
    return $googleDriver->redirect();
}

public function fromGoogle(Request $request)
{
    try {
/*
Solution Starts ----
*/
        if (empty($_GET)) {
            $t = parse_url($_SERVER['REQUEST_URI'], PHP_URL_QUERY);
            parse_str($t, $output);
            foreach ($output as $key => $value) {
                $request->query->set($key, $value);
            }
        }
/*
Solution Ends ----
*/
        /**
         * @var GoogleProvider $googleDriver
         */
        $googleDriver = Socialite::driver("google");
        print_r($googleDriver->user());
    } catch (\Exception $e) {
        print_r($e->getMessage());
    }

Ответ 15

На вашем контроллере в методе callback()

$ user = $service-> createOrGetUser (Socialite :: driver ('facebook') → user());

$user = $service->createOrGetUser(Socialite::driver('facebook')->stateless()->user());

Ответ 16

Эта проблема не имеет ничего общего с большинством решений, описанных выше, и является такой же простой, как изменение URL-адреса обратного вызова с "http://localhost:8000/callback/twitter на http://127.0.0.1:8000/callback/twitter в вашем config/services.php и в вашем приложении для твиттера, настроенном в вашем приложении для твиттера.

http://localhost в URL - это проблема, замените на http://127.0.0.1

Ответ 17

столкнулся с такой же проблемой
это решило мою проблему
$providerUser = Socialite:: with ('facebook') → user();

Ответ 18

Я хочу поделиться с вами своим решением. Я перехожу к моему файлу AbstractProvider.php и в строке проблемы

public function user()
{
    if ($this->hasInvalidState()) {
        throw new InvalidStateException;
    }

    // ...
}

Я останавливаю бросок нового InvalidStateException и вызываю функцию переадресации следующим образом:

public function user()
{
    if ($this->hasInvalidState()) {
        $this->redirect();
        // throw new InvalidStateException;
    }

    // ...
}