Функция авторизации через VK

В заметке описывается функция-заготовка, предназначенная для авторизации на сайте пользователей из ВКонтакте


Функция, описываемая в заметке, реализует только лишь проверку и получение данных о пользователе из соц. сети ВКонтакте в ваше приложение. В зависимости от того на каком движке разработан сайт, данные пришедшие от VK, можно обработать соответствующим образом в контексте того или иного движка или системы.

Сперва нужно настроить приложение во вконтакте. Создаем приложение:


create-app-vk


Затем редактировать » настройки, здесь нам понадобится id приложения, защищенный ключ, проставить базовый домен и проверить, чтобы был вкл. API, пример:


edit-app-vk

function auth_VK($id, $secret_key, $uri)
{
    if (!isset($_REQUEST['error'])) {
        $client_id = $id;
        $client_secret_key = $secret_key;
        $redirect_uri = $uri;
        $oauth_url = '';
        if (isset($_REQUEST['code']) && !empty($_REQUEST['code'])) {
            $code = trim(strip_tags($_REQUEST['code']));
            $params = [
                'client_id' => $client_id,
                'client_secret' => $client_secret_key,
                'code' => $code,
                'redirect_uri' => $redirect_uri
            ];
            $myCurl = curl_init();
            curl_setopt_array($myCurl, [
                CURLOPT_URL => 'https://oauth.vk.com/access_token',
                CURLOPT_RETURNTRANSFER => true,
                CURLOPT_POSTFIELDS => urldecode(http_build_query($params))
            ]);
            if ($chek = curl_exec($myCurl)) {
                $token = json_decode($chek);
                if ($token->error) {
                    /* Ошибка авторизации через VK! Смотрим коды ошибки
                     * Выкидываем исключение или выдаем сообщение
                     * Обрабатваем эту ситуацию
                     *  */
                } else {
                    /*
                     * Получение данных
                     * */
                    $email = $token->email;
                    if (isset($token->access_token)) {
                        $params = [
                            'uids' => $token->user_id,
                            'fields' => 'first_name,last_name,screen_name,bdate,photo_big',
                            'access_token' => $token->access_token
                        ];
                        curl_setopt_array($myCurl, [
                            CURLOPT_URL => 'https://api.vk.com/method/users.get',
                            CURLOPT_RETURNTRANSFER => true,
                            CURLOPT_POSTFIELDS => urldecode(http_build_query($params))
                        ]);
                        if ($chek = curl_exec($myCurl)) {
                            $info = json_decode($chek);
                            $uid = $info->response[0]->uid;
                            $first_name = $info->response[0]->first_name;
                            $last_name = $info->response[0]->last_name;
                            $bdate = $info->response[0]->bdate;
                            $photo_big = $info->response[0]->photo_big;
                            /*
                             * На этом этапе регистрация и авторизация пользователя
                             * Проверка на существующего пользователя, генерация пароля и тд
                             * Проверить на наличие в бд и зарегистриовать, или авторизовать пользователя
                             * детали реализации дальше опущены
                             * */
                        }
                    }
                }
            }
            curl_close($myCurl);
        } else {
            $params = [
                'client_id' => $client_id,
                'redirect_uri' => $redirect_uri,
                'display' => 'popup',
                'scope' => 'email',
                'response_type' => 'code'
            ];
            $oauth_url = 'https://oauth.vk.com/authorize?' . urldecode(http_build_query($params));
        }
        return ($oauth_url !== '') ? $oauth_url : false;
    } else {
        return false;
    }
}

Сама функция возвращает либо ссылку, которую можно повесить на кнопку "Войти через VK", либо false (в случае, когда пользователь успешно авторизовался или вывелась ошибка, в случае неудачной проверки, или по иным причинам). Там где должна выводится ссылка:

/*  инициализируем авторизацию, 
 * $redirect_uri — куда будет идти перенаправление, string
 *  например страница входа — site.com/login
 * $id — id приложения в ВК, integer
 * $secret_key — секретный ключ, string
 */

if ($oauth_url = auth_VK($id, $secret_key, $redirect_uri)){ 
   // $oauth_url содержит ссылку на авторизацию через VK
   ?><p><a href="<?= $oauth_url ?>" class="btn">Войти через VK</a></p><?
}

В качестве теста я создал приложение, в настройках выбрал всю необходимую информацию. Пошел проверять у себя на localhost в теме twentyseventeen на wordpress. Создал там страничку auth, шаблон:

<? get_header(); ?>
    <div class="wrap">
        <div id="primary" class="content-area">
            <main id="main" class="site-main" role="main">
                <?
                if ($oauth_url = auth_VK(5812210, 'vm0DqCqNPXyR1aAf0nTs', 'http://site.loc/auth/')) {
                    ?><p><a href="<?= $oauth_url ?>" class="btn">Войти через VK</a></p><?
                }
                ?>
            </main>
            <!-- #main -->
        </div>
        <!-- #primary -->
    </div><!-- .wrap -->
<? get_footer(); ?>

Clip2net_170226013902-min

А в файл functions.php саму функцию auth_VK. Только в самом конце подправил функцию, чтобы посмотреть возвращаемый результат:

/*
    * На этом этапе регистрация и авторизация пользователя
    * Проверка на существующего пользователя, генерация пароля и тд
    * Проверить на наличие в бд и зарегистриовать, или авторизовать пользователя
    * детали реализации дальше опущены
    * */
       echo '<pre>';
          var_dump( [
             'id' => $uid,
             'first_name' => $first_name,
             'last_name' => $last_name,
             'bdate' => $bdate,
             'photo_big' => $photo_big
           ] );
       echo '</pre>';

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

Clip2net_170226003913-min

А так, на самом деле, вместо этой распечакти массива, в этой функции дальше необходимо сделать множество вещей, таких как указано в комментариях к коду, — проверить пользователя по email у нас базе, зарегистрировать, если это новый юзер, выслать пароль к аккаунту на почту, авторизовать и прочее. Например, в контексте wordpress в дальнейшем можно было бы сделать примерно следующее:

/*
 * Проверить на наличие в бд и внести пользователя или авторизовать
 * */
global $wpdb;
$query = "SELECT * FROM `wp_users` WHERE `user_email` = '$email'";
$chekmail = $wpdb->get_results($query);
if (count($chekmail) == 0) {
    /*
     * Пользователя нет в БД
     * */
    $pass = wp_generate_password();
    /*
     * Зарегистрировать
     * */
    $userdata = [
        'ID' => 0
        , 'user_pass' => $pass
        , 'user_login' => $email
        , 'user_nicename' => 'vk_' . $uid
        , 'user_email' => $email
        , 'display_name' => $first_name
        , 'first_name' => $first_name
        , 'last_name' => $last_name
        , 'description' => 'Пользователь, авторизованный через VK'
        , 'rich_editing' => true
        , 'role' => 'subscriber'
    ];
    wp_insert_user($userdata);
    /*
     * Авторизовать по паролю
     * */
    $credentials = [
        'user_login' => $email,
        'user_password' => $pass
    ];
    if (is_wp_error($user = wp_authenticate($credentials['user_login'], $credentials['user_password']))) {
        // Ошибка
        ?><p class="alert alert-danger"><?= $user->get_error_message() ?></p><?
    } else {
        nocache_headers();
        wp_clear_auth_cookie();
        wp_set_auth_cookie($user->ID);
        wp_redirect($uri);
        /*
         * Отправить на емаил pass к аккаунту
         * */
        $to = [$email];
        $headers = 'MIME-Version: 1.0' . "\r\n";
        $headers .= 'Content-type: text/html; charset=utf-8' . "\r\n";
        $headers .= 'From: site.loc <admin@site.loc>' . "\r\n";
        $subj = "Спасибо за регистрацию в блоге";
        $what = "<h3>Спасибо за регистрацию в блоге, через VK, " . $first_name . "!</h3>";
        $what .= "<p>Привет! Твой пароль: " . $pass . " , логин — " . $email . " , если заходишь через /wp-admin/ , или просто на странице /auth/ все также через VK</p>";
        wp_mail($to, $subj, $what, $headers);
    }
} else {
    /*
     * Пользователь уже зарегистрирован, просто авторизовать
     * ...
     * */
}


Похожие заметки:

Веб-разработка

Займусь вашим проектом, если вам нужен специалист в области веб-разработки

Открыть здесь

279

Вывод комментариев с пагинацией

Выводим все комменты на WordPress из базы данных с пагинацией

Открыть здесь

1322

Прикручиваем Sphinx к своему поиску на сайте

Установка, задание конфигурации и запуск службы на Ubuntu для высокоскоростного поиска. Быстрый гайд

Открыть здесь

3015


Перед тем как писать комментарии, рекомендую ознакомиться:

Markdown синтаксис »

Оформление кода »

Нужна аватарка »

Комментарии


1
avatar

Вася сказал 31-07-2018 в 11:50


Добрый день! а можно код именно авторизации а не регистрации?