Přejít k navigační liště

Zdroják » PHP » Aplikace pro Facebook, díl II. – autorizace

Aplikace pro Facebook, díl II. – autorizace

V druhém díle seriálu o tvoření aplikací pro dnes nejpopulárnější sociální síť – Facebook – si představíme princip autorizace aplikace, podíváme se na protokol OAuth, který ověřuje přístupová práva ke Graph API, a nakonec si vše názorně předvedeme na ukázce.

minulém díle našeho seriálu jsme vytvořili „Hello world“ aplikaci v PHP za použití oficiální Facebook knihovny. Řekli jsme si, že aplikace na Facebooku jsou „obyčejné“ webové stránky, běžící na vašem serveru, a do Facebooku vložené IFRAMEm.

Dnes se podíváme na:

  • Princip autorizace (získání extended_permis­sions) pro aplikaci
  • Princip protokolu OAuth použitého pro přístup ke Graph API
  • Ukázku autorizace pomocí PHP (server-side) a JavaScriptu (client-side)

Autorizace aplikace na Facebooku

Většina dat dostupných přes Graph API není veřejná. V praxi to znamená, že po spuštění aplikace u uživatele (je jedno, jestli v záložce nebo jako standardní aplikace) je potřeba aplikaci autorizovat a získat tak klíč (tzv. access_token) s vámi definovanými možnostmi (extended_per­missions – seznam práv, která vyžadujete po uživateli).

Do extended_permis­sions spadá např.:

  • posílání wallpostů
  • nahrávání fotek
  • likování komentářů
  • správa stránek apod.

Access_token má ve výchozím stavu omezenou časovou platnost, po které je potřeba získat klíč nový. Při získávání nového tokenu u již autorizované aplikace se Facebook na udělení extended_permis­sions uživatele neptá a klíč rovnou poskytne.

Speciálním případem je tzv. Offline access (jedno z extended_per­missions), který umožní získat access_token s neomezenou platností (a to i pro případ, kdy se uživatel odhlásí z Facebooku). Offline access se však spíše hodí pro webové služby s Facebook Connectem nebo na speciality s použitím CRONu, na běžné aplikace nám postačí access_token bez Offline accessu.

Protokol OAuth2

Facebook používá pro zabezpečení Graph API standardní OAuth protokol ve verzi 2. Nebudeme se zde pouštět do podrobností, o samotném protokolu si můžete přečíst článek zde na Zdrojáku.

OAuth na Facebooku ve zkratce

  1. Vytvoříme autorizační URL, která vede k zobrazení OAuth dialogu. Autorizační URL obsahuje ID aplikace, extended_permis­sions a redirect_uri – adresu, na kterou je uživatel následně zpět přesměrován.
  2. Pokud uživatel povolí přístup aplikace v dialogu, je přesměrován na redirect_uri s autorizačním kódem v GET parametru
  3. Kombinací autorizačního kódu a App_secret (tajný klíč aplikace dostupný ve vývojářské aplikaci, který s nikým nesdílejte) získáte nakonec access_token.
  4. S access_tokenem už můžete vesele posílat požadavky na API.

Pozn.: Pokud vyprší platnost access_tokenu, je při získávání nového přeskočen krok se zobrazením dialogu (tzn. že uživatel je okamžitě přesměrován na redirect_uri).

PHP autorizace

V aplikaci vycházíme z kódu předchozího dílu.

Budeme pracovat s námi vytvořenou session přihlášeného uživatele a podle potřeby přesměrujeme uživatele na OAuth dialog:

define('EXTENDED_PERSMISSIONS', 'publish_stream');

// Uživatel není přihlášen || Neautorizoval aplikaci
if (!isset($_SESSION["user_logged"])) {
    $redirect_uri = CANVAS_PAGE . "?foo=bar";
    echo("<script> top.location.href='" . $facebook->getLoginUrl(array("scope" => EXTENDED_PERSMISSIONS, "redirect_uri" => $redirect_uri)) . "'</script>");
}

Pokud se uživatel vrátí zpět na redirect_uri, získáme autorizační token (ten použijeme pro získání access_tokenu):

            // Uživatel povolil autorizaci a vrací se na redirect_uri
if (isset($_REQUEST["code"])) {
    $_SESSION["user_logged"] = TRUE;

    // Zbavíme se "?code" z URL
    echo("<script> top.location.href='" . CANVAS_PAGE . "'</script>");
}

Jestliže uživatel autorizaci zamítne (nebo se autorizace z nějakého důvodu nepovede), dozvíme se o tom následovně:

// Uživatel nepovolil autorizaci aplikace
    if (isset($_REQUEST['error'])) {
    die("Uzivatel zamitnul autorizaci aplikace!");
    }

Wallpost

Nyní, když máme autorizovanou aplikaci<a>* a publish_stream práva, můžeme se pustit do samotného wallpostu.

Poznámka:

*) V této aplikaci uložení access_tokenu necháváme na knihovně. Není však problém získat a uložit access_token manuálně a mít tedy i tuto část plně pod kontrolou. Po obdržení autorizačního kódu od uživatele získáte access_token např. přes file_get_contents() z: 

https://graph.facebook.com/oauth/access_token?
     client_id=APP_ID&redirect_uri=REDIRECT_URI&
     client_secret=APP_SECRET&code=AUTORIZACNI_KOD

Graph API předáme wallpost jako klasické pole:

$wall_post_attachment = array(
          'message' => 'Testovací wallpost z mojí aplikace',
          'name' => 'Zdroják.cz',
          'caption' => "Tvorba webových stránek a aplikací",
          'link' => 'https://www.zdrojak.cz',
          'description' => 'Denní zpravodajství pro webové vývojáře, kodéry...',
          'picture' => 'http://i.iinfo.cz/z/logo-zd.gif');

Komunikaci s API zajišťuje metoda api().

    try {
    // Odešleme Wallpost pomocí Graph API na Facebook
    $result = $facebook->api('/me/feed/', 'post', $wall_post_attachment);
    } catch (FacebookApiException $e) {
    echo "Chyba: " . $e->getMessage();
    }

První parametr metody api jsou data, s kterými pracujeme a uživatelské id (v tomto speciálním případě označuje „me“ aktuálně přihlášeného uživatele). Dostupné jsou např.:

  • me/likes
  • me/movies
  • me/notest atd.

Druhý parametr specifikuje, zda data přijímáme nebo odesíláme (POST || GET). A poslední parametr je samotný Wallpost.

Celou aplikaci si můžete stáhnout zde.

Autorizace pomocí JavaScript SDK

Autorizace pomocí JS SDK je poměrně jednoduchá. Ve srovnání s autorizací na straně serveru se hodí lépe pro webové stránky propojené s Facebookem (např. pokud chcete na své službě umožnit uživateli přihlášení pomocí Facebooku). Nehodí se pro stránky a aplikace, které jsou funkčně závislé na Facebooku již při startu, a to především proto, že autorizační dialog nelze zobrazit při načtení stránky, protože ho prohlížeč s největší pravděpodobností zablokuje (automaticky vyskakující pop-up). Je tedy třeba autorizaci volat např. na onclick událost tlačítka. Níže je ukázka zdrojového kódu, který umožní pomocí tlačítek autorizovat (přihlásit se k) aplikaci, odhlásit se z aplikace a aplikaci deautorizovat (odebrat jí práva). V příkladu je použita jQuery. Podrobné vysvětlení je k nalezení přímo v kódu:

index.html

<!DOCTYPE html>
<html lang="cs-cz" dir="ltr">
<head>
<meta charset="UTF-8">
<title>JS AUTH zdroják</title>

<!-- jQuery - www.jquery.com -->
<script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.6.4/jquery.min.js"></script>
</head>
<body>

<!-- Na tento div nezapomeňte, Facebook si do něj natahá svá data -->
<div id="fb-root">
</div>

<!-- Vzdáleně includujeme JS SDK  -->
<script type="text/javascript" src="http://connect.facebook.net/cs_CZ/all.js"></script>

<!-- soubor s našimi funkcemi (obsah níže) -->
<script type="text/javascript" src="./fbfunctions.js"></script>


<script type="text/javascript">
//inicializujeme knihovnu, všimněte si, že narozdíl od PHP SDK není třeba secret key
FB.init({
    appId : 114242578683200,
    status : true,
    cookie : true,
    xfbml : true,
    oauth: true
});

//Zjistí zda existuje session uživatele a vykoná funkci handleSessionResponse  (callback)
FB.getLoginStatus(handleSessionResponse);

</script>

<!-- Uživatele požádá o přihlášení a pokud není autorizován i o autorizaci -->
<button id="login" onclick="login()">Login</button>

<!-- Uživatele odhlásí z aplikace -->
<button id="logout" onclick="logout()">Logout</button>

<!-- Uživatele odhlásí z aplikace a odebere autorizaci -->
<button id="disconnect" onclick="disconnect()">Disconnect</button>

<!-- Sem vložíme obsah dle stavu uživatele -->
<div id="content">
</div>

</body>
</html>

fbfunctions.js

/* Přihlášení / autorizace uživatele. V případě, že autorizace ještě neproběhla, je uživateli zobrazen autorizační dialog, jinak je pouze vytvořena session a uživatel nic nepozoruje    */
function login(){
    FB.login(handleSessionResponse, {
        scope: 'publish_stream' // jednotlivá práva oddělujeme čárkami bez mezery
    });
}

/* Odhlášení uživatele z aplikace */
function logout() {
   FB.logout(handleSessionResponse);
}

 /* Odhlášení a odebrání autorizace uživatele */
function disconnect() {
               if (response.authResponse) {
          FB.api('/me/permissions', 'delete', function(response) {
                  $('#content').html('<p>Uživatel odhlášen a práva odebrána</p>');
             });
           }
    
}

/*callback, zjistí zda byla vytvořena session a dle toho zobrazí požadovaný obsah */
function handleSessionResponse(response){
        var res = response.authResponse;
    if (!res) { //pokud nemáme platnou session uživatele
        $('#content').html('<p>Uživatel není přihlášen</p>');
    }
    else { //pokud máme session uživatele a uživatel tedy je přihlášený
                   
        FB.api(
          {
            method: 'fql.query',
            query: 'SELECT name, pic FROM profile WHERE id=' + res.userID //res obsahuje např i access_token, který můžeme využít pro získání neveřejných dat
            
          },
          function(response) {
            var user = response[0];
            $('#content').html('<img src="' + user.pic + '">' + user.name);
          
          }
        );
    }
    
   
}

Závěr

V dnešním díle jsme si ukázali tu nejdůležitější část pro tvorbu aplikací na Facebooku. S tímto základem jsme schopni do své aplikace implementovat veškerou dostupnou funkcionalitu Facebooku.

V dalším díle se zaměříme na novinky představené na nedávné konferenci F8 (kdy, kde). Konkrétně se bude jednat o:

  • Activities v Graph API
  • Timeline API
  • Notifications

Komentáře

Subscribe
Upozornit na
guest
13 Komentářů
Nejstarší
Nejnovější Most Voted
Inline Feedbacks
View all comments
facebok zbytečnost

Ffacebok je zbytečnost.

Ty jsi ale jeliman

Ale na váš zbytečný ppost nikdy mít nebude :p.

Michal

Reknete to tem firmam, ktere kvuli nemu zrizuji specielni oddeleni s lidmi, kteri neprogramuji nic jineho a firme vydelavaji

Láďa

Chápu že seriál vznikal asi v předstihu, ale aktualizace na OAuth 2.0 je známá už od května, od 1. října vyžadovaná a příklady by s ní měly počítat.

Václav Dohnal

Příklady v článku jsou pro OAuth2, viz článek:

Facebook používá pro zabezpečení Graph API standardní OAuth protokol ve verzi 2…

Láďa

Potom by ale měl být ve FB.init parametr oauth nastavený na true. A FB.login taky vypadá jinak: https://developers.facebook.com/docs/reference/javascript/FB.login/

Jan Prachař

Jo taky jsem si všiml, že asi ještě týden po 1. říjnu fungoval OAuth 1. Nevíte, jak je to teď?

cimenta

Ja si chci napsat aplikaci v php (spoustena cronem), co mi bude ukladat „updates“ my pratel a vybranych „page“ z facebooku do wordpressu jako posts.

Urcite muzu pouzit neco z prvnich dvou dilu, ale potrebuji poradit, jak na to, protoze mi pripadne, ze vse, co potrebuji nebylo v clancich popsano.

dik. R

shneck

Dobrý den. Asi to neni úplně k tématu a téma samotné je taky pár let staré, ale za zkoušku nic nedám. Mám webovou stránku, FB aplikaci a FB stránku. Potřeboval bych poradit s provedením PHP skriptu, který při přidání předmětu na webové stránky o tom poslal krátkou zprávičku na FB stránky prostřednictvím FB aplikace. Trávím nad tím celý den, v podstatě to funguje, ale jen hodinu po mém přihlášení na FB (krátká životnost access_token). Skript bych potřeboval automatizovaný, bez nutnosti mojeho přihlášení. Nevěděl by si někdo rady prosím?

Enum a statická analýza kódu

Mám jednu univerzální radu pro začínající programátorty. V učení sice neexistují rychlé zkratky, ovšem tuhle radu můžete snadno začít používat a zrychlit tak tempo učení. Tou tajemnou ingrediencí je statická analýza kódu. Ukážeme si to na příkladu enum.