Answer the question
In order to leave comments, you need to log in
What is the best way to get access_token in VK?
Hello!
My task is to get an access_token from Vkontakte to enter it into the database.
Must be obtained from this link:
// https://oauth.vk.com/authorize?client_id=111111&scope=wall,photos,offline&redirect_uri=http://api.vk.com/blank.html&display=wap&response_type=token
// http://api.vk.com/blank.html#access_token=11111111111111111111111111111111111111111111111111111111111111111111&expires_in=0&user_id=11111111
Answer the question
In order to leave comments, you need to log in
This is how I do it and it works:
in JavaScript I follow a link
in the script vk_login.php I write the following:
$vk_app_id = ''; // id вашего приложения
$vk_app_secret = ''; // секретный ключ вашего приложения
$url = 'https://oauth.vk.com/access_token?client_id='.$vk_app_id.'&client_secret='.$vk_app_secret.'&code='.$_REQUEST['code'].'&redirect_uri=http://'.$_SERVER['SERVER_NAME'].'/vk_login.php';
$result = file_get_contents($url);
$result = json_decode($result, true);
$access_token = $result['access_token'];
// дальше то, что требуется
None of the respondents have ever worked with VK, it seems. So at least they didn't answer :)
The question is why do you need such wide rights for the application? Are you going to use methods that require Standalone?
There is no way to hide this token except for copying, unless of course you do it through your own browser or if in a desktop application.
> How to pull out access_token and close the window so that a person would not bother with manual copying of access_token ?
> Maybe there are other ways to get it?
I made the ability to automatically copy the token.
The bottom line is that you collect the headers of all 3 requests:
1. the request where cliend_id, scope and redirect_uri are specified returns the Location to the second request
2. the second request will return the Location to the redirect_uri, this is where our access_token will be.
3. The title to your redirect_uri.
Then, with the usual regular expression, you pull out Location from the third request. Approximately it looks like this:
<?
class VKClass {
protected $email = "TELEPHONE";
protected $pass = "PASSWORD";
protected $auth_url = "https://m.vk.com";
protected $cookie = "cookie.txt";
protected $client_id = "XXXXXXX";
protected $redir_url = "http://goto.ru/token";
public function __construct() {
//вызываем метод для загрузки необходимых объектов
if(empty($_SESSION["loggedIn"]))
$this->logIn();
if(empty($_SESSION["access_token"]))
$this->getAccessToken();
}
public function prependCurl($options){
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $options["url"]);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, 0);
curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 0);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, $options["flocation"]);
curl_setopt($ch, CURLOPT_POST, $options["post"]);
curl_setopt($ch, CURLOPT_HEADER, $options["header"]);
if($options["post"])
curl_setopt($ch, CURLOPT_POSTFIELDS, $options["postdata"]);
if($options["cookie_w"])
curl_setopt($ch, CURLOPT_COOKIEJAR, $_SERVER["DOCUMENT_ROOT"].$this->cookie);
if($options["cookie_r"])
curl_setopt($ch, CURLOPT_COOKIEFILE, $_SERVER["DOCUMENT_ROOT"].$this->cookie);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$data = curl_exec($ch);
curl_close($ch);
return $data;
}
public function logIn(){
$options = ["url" => $this->auth_url, "flocation" => 0, "post" => 0, "header" => 0, "cookie_w" => 1, "cookie_r" => 0];
$login_page = $this->prependCurl($options);
unset($options);
//функция str_get_html используется из бибилиотеки Simple HTML DOM Parser
$html = str_get_html($login_page);
$login_url = @$html->find("form",0)->action;
$options = ["url" => $login_url, "flocation" => 1, "post" => 1, "header" => 0, "postdata" => ["email" => $this->email, "pass" => $this->pass], "cookie_w" => 1, "cookie_r" => 1];
$this->prependCurl($options);
$_SESSION["loggedIn"] = $this->loggedIn= true;
}
public function getLocations($url){
$options = ["url" => $url, "flocation" => 1, "post" => 0, "header" => 1, "cookie_w" => 1, "cookie_r" => 1];
$data = $this->prependCurl($options);
return $data;
}
public function getAccessToken(){
//по ссылке возвращается access_token. собираем все заголовки запросов
$url = "https://oauth.vk.com/authorize?client_id=".$this->client_id."&redirect_uri=".$this->redir_url."?display=page&response_type=token";
$headers = $this->getLocations($url);
//разбиваем на кол-во запросов
$hdrs = explode("\r\n\r\n", $headers);
//т.к. у нас 2 редиректа (с oauth.vk.com на login.vk.com и с login.vk.com на домен), то нам нужен второй запрос ($hdrs[1]), где соджержится access_token
preg_match("/Location: (.*)/m", $hdrs[1], $matches);
//вырезаем наш access_token из ссылки что нам прислал вк сервер
@preg_match("/#access_token=(.*?)&/", $matches[1], $token);
//объявляем access_token в сессии и в классе
@$_SESSION["access_token"] = $this->access_token = $token[1];
}
}
if (document.location.search.match(/[?|&]client_id=(\d+)&*$/)) {
client_id = RegExp.$1
}
User Igor asked to describe the solution in more detail. Yes, easily:
_
Так как наше окошко, вызываемое с "Something Page" (далее SP), мы планируем натравить на домен https://oauth.vk.com/, а оттуда получить редиректом в ногу, то мы не сможем повесить на него какие-либо события, типа того же onload. Вследствие чего, нам никак не удастся отследить факт перехода на наш RedirectURI (или на страницу ошибки).
Вывод напрашивается простой - страница RedirectURI должна нам сама о себе сообщить после загрузки. Для этого достаточно организовать общение между двумя нашими окнами посредством postMessage. То есть, с RedirectURI отправляем, а на "SP" подписываемся на событие и ловим.
And so, let's go:
var getToken = (function (Win, tokenWindow){
/**
* (Win, tokenWindow)
*
* @param {Window} Win
* @param {Null} tokenWindow
*
* @return {Function} getToken
*/
//ID приложения
var OPTION_APP_ID = 1234567;
//Ссылка для перенаправления (должна быть указана в настройках приложения)
var OPTION_APP_REDIRECT = "http://mysite.ru/vkAuth.php?action=get_token";
//Запрашиваемые права
var OPTION_APP_SCOPE = ["wall", "photos", "offline"];
function http_build_query(obj){
/**
* http_build_query(obj)
*
* @param {Object} obj
*
* @return {String}
*/
var k, res = "";
for(k in obj){
res += ("&" + k + "=" + Win.encodeURIComponent(obj[k]));
}
return res.slice(1);
}
function openTokenWindow(app, redirect, scope){
/**
* openTokenWindow(app, redirect, scope)
*
* @param {Number|String} app
* @param {String} redirect
* @param {Array} scope
*
* @return {Window}
*/
return Win.open("https://oauth.vk.com/authorize?" + http_build_query(
{
"client_id" : app,
"scope" : scope.join(","),
"redirect_uri" : redirect,
"display" : "wap",
"response_type" : "token"
}),
"Авторизация",
(
"menubar=yes," +
"status=yes," +
"toolbar=yes," +
"location=no," +
"resizable=yes," +
"scrollbars=yes," +
"left=50," +
"top=50," +
"width=500," +
"height=500"
)
);
}
return function getToken(callbackSuccess, callbackError){
/**
* getToken(callbackSuccess, callbackError)
*
* @param {Function} callbackSuccess
* @param {Function} callbackError
*
* @return {Undefined}
*/
if(tokenWindow && !tokenWindow.closed){
return alert("Уже открыто окно авторизации"), undefined;
}
tokenWindow = openTokenWindow(OPTION_APP_ID, OPTION_APP_REDIRECT, OPTION_APP_SCOPE);
Win.addEventListener("message", function x(e){
var message = e.data, source = e.source;
if(source === tokenWindow){
tokenWindow = tokenWindow.close(), null;
Win.removeEventListener("message", x);
message = JSON.parse(message);
message.errno ? callbackSuccess(message.token) : callbackError();
}
});
}
})(window, null);
getToken(
function(x){
//Функция, которая будет вызвана при успешной авторизации
alert("Токен:" + x);
},
function(){
//Функция, которая будет вызвана при ошибке
alert("Ошибка");
}
);
redirectURI#access_token={token}&....
, где наше искомое значение - это {token}
!function(hash, win, reg){
/**
* (hash, win, reg)
*
* @param {String} hash
* @param {*} win
* @param {RegExp} reg
*
* @return {Undefined}
*/
//На самом деле, достаточно просто уведомить opener о том, что авторизация успешна.
//А сам токен выдирать из tokenWindow.location.hash
//Но зачем...
var data = reg.exec(hash), token = data && data[1];
win && win.postMessage(
JSON.stringify(
{
errno : data,
token : token
}
)
);
//need targetOrigin condition?
}(location.hash, opener, /access_token=([^&]+)/);
Didn't find what you were looking for?
Ask your questionAsk a Question
731 491 924 answers to any question