<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Krotscheck.net &#187; facebook</title>
	<atom:link href="http://www.krotscheck.net/tag/facebook/feed" rel="self" type="application/rss+xml" />
	<link>http://www.krotscheck.net</link>
	<description>Michael Krotscheck's insights, ideas, and inspirations about web technology, life, and the kitchen sink.</description>
	<lastBuildDate>Fri, 03 Feb 2012 05:10:42 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=</generator>
		<item>
		<title>Zend_Auth_Adapter_Facebook</title>
		<link>http://www.krotscheck.net/2010/08/21/zend_auth_adapter_facebook.html</link>
		<comments>http://www.krotscheck.net/2010/08/21/zend_auth_adapter_facebook.html#comments</comments>
		<pubDate>Sat, 21 Aug 2010 22:00:13 +0000</pubDate>
		<dc:creator>Michael Krotscheck</dc:creator>
				<category><![CDATA[Blog]]></category>
		<category><![CDATA[Auth]]></category>
		<category><![CDATA[facebook]]></category>
		<category><![CDATA[zend]]></category>

		<guid isPermaLink="false">http://www.krotscheck.net/2010/08/21/zend_auth_adapter_facebook.html</guid>
		<description><![CDATA[This post is rather more nerdy than my other ones, and goes to describe how to create a Facebook authentication adapter for the Zend Framework, using the new Facebook Graph API. I do not intend to support this code explicitly, but I do work with it and will update it to suit my own needs. [...]]]></description>
			<content:encoded><![CDATA[<p>This post is rather more nerdy than my other ones, and goes to describe how to create a Facebook authentication adapter for the Zend Framework, using the new Facebook Graph API. I do not intend to support this code explicitly, but I do work with it and will update it to suit my own needs. If you&#8217;re impatient, the full code for the adapter and a sample controller are the last two code samples at the bottom of this post.</p>
<h3>A discussion about OAuth and OpenID</h3>
<p>Strictly speaking, Facebook supports <a href="http://oauth.net/" target="_blank">OAuth</a>, not <a href="http://openid.net/foundation/" target="_blank" title="The OpenID Foundation">OpenID</a>. OAuth is a way for your application to act on behalf of someone else on another side, while OpenId exists solely for you to use the other website as an authorization authority. The difference is subtle, however telling that Facebook has explicitly stated that it does not want to be an authorization authority. In practice, however, the two standards are interchangeable, and OAuth works pretty well as a way to authenticate a user.</p>
<h3>How Facebook Auth Actually Works</h3>
<p>Here&#8217;s the flow in four easy steps:</p>
<ol>
<li>The user clicks on a &#8220;Login to Facebook&#8221; link on your server, which redirects them to another page on your server that handles the authentication.</li>
<li>Your Facebook Auth page puts all the parameters for your authentication, such as your app ID and scope, into a URL and sends the user to Facebook via that URL.</li>
<li>Once Facebook returns the user (presumably authenticated) to your server, you can use the parameters sent via the URL to request an authentication token from Facebook. This is done via curl or some other server-to-server communication by calling the graph API.</li>
<li>You use this authentication token to access the user&#8217;s information on Facebook.</li>
</ol>
<h4>Step 1: Get all the data you need</h4>
<p>To properly authenticate with Facebook, you need four pieces of data. The first two are your application id and your application secret, both of which are available on your developer application page.</p>
<div class="image">
  <img src="http://www.krotscheck.net/wp-content/uploads/2010/08/Screen-shot-2010-08-21-at-1.50.04-PM.png" width="479" height="480" alt="Screen shot 2010-08-21 at 1.50.04 PM.png" /></p>
<p>A sample Facebook application page</p>
</div>
<p>The second two pieces of data are specific to your implementation. These are the redirect URI, which is used to tell Facebook where to send the user once they are done authorizing your application, and the permission scope, which you use to tell Facebook what permissions you want to request from the user. This latter one actually warrants some more documentation, which Facebook has graciously provided <a href="http://developers.facebook.com/docs/authentication/permissions" target="_blank">here</a>. Be careful: Users can get really suspicious if you ask for too much data.</p>
<h4>Step 2: Redirect your user to Facebook.</h4>
<p>With this data, you can redirect your user to Facebook. Facebook will then work some magic and ask the user whether they want to grant your application access to their profile. Don&#8217;t forget to urlencode that Redirect URI.</p>
<div class="code">
<pre>
$loginUri = "https://graph.facebook.com/oauth/authorize?client_id={$appId}&amp;redirect_uri={$redirectUri}&amp;scope={$scope}";
header('Location: ' . $loginUri);
</pre>
</div>
<h4>Step 3: Request an Auth Token</h4>
<p>Assuming that the user authorizes your application, Facebook will return them to your redirect URI with the &#8220;code&#8221; parameter in the URL. You can use this parameter to request an authorization token from Facebook. In this case I&#8217;m using the Zend Request handler to simplify things a little.</p>
<div class="code">
<pre>
$client = new Zend_Http_Client( "https://graph.facebook.com/oauth/access_token" );
$client-&gt;setParameterGet('client_id', $appId);
$client-&gt;setParameterGet('client_secret', $secret);
$client-&gt;setParameterGet('code', $code);
$client-&gt;setParameterGet('redirect_uri', $redirectUri);

$result = $client-&gt;request('GET');
$params = array();
parse_str($result-&gt;getBody(), $params);
$token = $params['access_token'];</pre>
</div>
<h4>Step 4: Read the user&#8217;s profile</h4>
<p>At this point, you have an auth token that grants you access to read the user&#8217;s profile information in accordance to the permissions they have granted you. These permissions are completely blind- you don&#8217;t have to additionally specify what you want to access &#8211; the requests will simply return the information to which you have access.</p>
<div class="code">
<pre>
$client = new Zend_Http_Client( "https://graph.facebook.com/me" );
$client-&gt;setParameterGet('client_id', $appId);
$client-&gt;setParameterGet('access_token', $token);
$result = $client-&gt;request('GET');
$user = json_decode($result-&gt;getBody());</pre>
</div>
<h4>Zend_Auth_Adapter_Facebook</h4>
<p>For those of you who would rather not take the above code and wrap it into your own Auth Adapter, I&#8217;ve gone ahead and done all that work for you. Below you will find a sample Zend Controller, as well as a pre-baked Auth Adapter. If you come across any major security problems in it, I&#8217;d love to know, since I use this adapter myself <img src='http://www.krotscheck.net/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> .</p>
<div class="code">
<p>file: Zend/Auth/Adapter/Facebook.php</p>
<pre>
class Zend_Auth_Adapter_Facebook implements Zend_Auth_Adapter_Interface
{
    /**
     * The Authentication URI, used to bounce the user to the facebook redirect uri.
     *
     * @var string
     */
    const AUTH_URI = 'https://graph.facebook.com/oauth/authorize?client_id=%s&amp;redirect_uri=%s';

    /**
     * The token URI, used to retrieve the OAuth Token.
     *
     * @var string
     */
    const TOKEN_URI = 'https://graph.facebook.com/oauth/access_token';

    /**
     * The user URI, used to retrieve information about the user.
     *
     * @var string
     */
    const USER_URI = 'https://graph.facebook.com/me';

    /**
     * The application ID
     *
     * @var string
     */
    private $_appId = null;

    /**
     * The application secret
     *
     * @var string
     */
    private $_secret = null;

    /**
     * The authentication scope (advanced options) requested
     *
     * @var string
     */
    private $_scope = null;

    /**
     * The redirect uri
     *
     * @var string
     */
    private $_redirectUri = null;

    /**
     * Constructor
     *
     * @param string $appId the application ID
     * @param string $secret the application secret
     * @param string $scope the application scope
     * @param string $redirectUri the URI to redirect the user to after successful authentication
     */
    public function __construct($appId, $secret, $redirectUri, $scope)
    {
        $this-&gt;_appId = $appId;
        $this-&gt;_secret = $secret;
        $this-&gt;_scope = $scope;
        $this-&gt;_redirectUri   = $redirectUri;
    }

    /**
     * Sets the value to be used as the application ID
     *
     * @param  string $appId The application ID
     * @return Zend_Auth_Adapter_Facebook Provides a fluent interface
     */
    public function setAppId($appId)
    {
        $this-&gt;_appId = $id;
        return $this;
    }

    /**
     * Sets the value to be used as the application secret
     *
     * @param  string $secret The application secret
     * @return Zend_Auth_Adapter_Facebook Provides a fluent interface
     */
    public function setSecret($secret)
    {
        $this-&gt;_secret = $secret;
        return $this;
    }

    /**
     * Sets the value to be used as the application scope (array())
     *
     * @param  string $scope The application scope
     * @return Zend_Auth_Adapter_Facebook Provides a fluent interface
     */
    public function setApplicationScope($scope)
    {
        $this-&gt;_scope = $scope;
        return $this;
    }

    /**
     * Sets the redirect uri after successful authentication
     *
     * @param  string $redirectUri The redirect URI
     * @return Zend_Auth_Adapter_Facebook Provides a fluent interface
     */
    public function setRedirectUri($redirectUri)
    {
        $this-&gt;_redirectUri = $redirectUri;
        return $this;
    }

    /**
     * Authenticates the user against facebook
     * Defined by Zend_Auth_Adapter_Interface.
     *
     * @throws Zend_Auth_Adapter_Exception If answering the authentication query is impossible
     * @return Zend_Auth_Result
     */
    public function authenticate()
    {
    	// Get the request object.
    	$frontController = Zend_Controller_Front::getInstance();
    	$request = $frontController-&gt;getRequest();

    	// First check to see wether we're processing a redirect response.
    	$code = $request-&gt;getParam('code');

    	if ( empty ($code ) )
    	{
	    	// Create the initial redirect
	    	$loginUri = sprintf(Zend_Auth_Adapter_Facebook::AUTH_URI , $this-&gt;_appId, $this-&gt;_redirectUri);

	    	if ( !empty($this-&gt;_scope) )
	    	{
	    		$loginUri .= "&amp;scope=" . $this-&gt;_scope;
	    	}

	    	header('Location: ' . $loginUri );
    	}
    	else
    	{
    		// Looks like we have a code. Let's get ourselves an access token
	    	$client = new Zend_Http_Client( Zend_Auth_Adapter_Facebook::TOKEN_URI );
	    	$client-&gt;setParameterGet('client_id', $this-&gt;_appId);
	    	$client-&gt;setParameterGet('client_secret', $this-&gt;_secret);
	    	$client-&gt;setParameterGet('code', $code);
	    	$client-&gt;setParameterGet('redirect_uri', $this-&gt;_redirectUri);

	    	$result = $client-&gt;request('GET');
	    	$params = array();
	    	parse_str($result-&gt;getBody(), $params);

	    	// REtrieve the user info
	    	$client = new Zend_Http_Client(Zend_Auth_Adapter_Facebook::USER_URI );
	    	$client-&gt;setParameterGet('client_id', $this-&gt;_appId);
	    	$client-&gt;setParameterGet('access_token', $params['access_token']);
	    	$result = $client-&gt;request('GET');
	    	$user = json_decode($result-&gt;getBody());

            return new Zend_Auth_Result( Zend_Auth_Result::SUCCESS, $user-&gt;id, array('user'=&gt;$user, 'token'=&gt;$params['access_token']) );
    	}

        return new Zend_Auth_Result( Zend_Auth_Result::FAILURE, null, 'Error while attempting to redirect.' );
    }
}
</pre>
</div>
<div class="code">
<p>file: modules/default/controllers/FacebookauthController.php</p>
<pre>
/**
 * Sample Facebook Auth Controller.
 *
 * @author Michael Krotscheck
 */
class FacebookauthController extends Zend_Controller_Action
{
	/**
	 * Application default action
	 */
	public function indexAction ()
	{
		$appId = 'YOUR_APP_ID';
		$secret = 'YOUR_APP_SECRET';
		$redirectUri = 'http://path-to-this-controller-and-action';
		$scope = 'YOUR_COMMA_SEPARATED_APPLICATION_SCOPE';

		// Create the authentication adapter.
		$adapter = new Zend_Auth_Adapter_Facebook( $appId, $secret, $redirectUri, $scope );

		// Get an authenticator instance
		$auth = Zend_Auth::getInstance();

		// This call will automatically redirect to facebook with the passed parameters.
		$result = $auth-&gt;authenticate($adapter);

		if ( $result-&gt;isValid() )
		{
			// Get the messages
			$messages = $result-&gt;getMessages();

			// Get the user object from the returned messages.
			$fbUser = $messages['user'];

			var_dump($fbUser);
		}
	}
}
</pre>
</div>
]]></content:encoded>
			<wfw:commentRss>http://www.krotscheck.net/2010/08/21/zend_auth_adapter_facebook.html/feed</wfw:commentRss>
		<slash:comments>14</slash:comments>
		</item>
		<item>
		<title>How to Publish a Flash Application to the Facebook Stream</title>
		<link>http://www.krotscheck.net/2009/12/21/how-to-publish-a-flash-application-to-the-facebook-stream.html</link>
		<comments>http://www.krotscheck.net/2009/12/21/how-to-publish-a-flash-application-to-the-facebook-stream.html#comments</comments>
		<pubDate>Mon, 21 Dec 2009 20:19:23 +0000</pubDate>
		<dc:creator>Michael Krotscheck</dc:creator>
				<category><![CDATA[Blog]]></category>
		<category><![CDATA[facebook]]></category>
		<category><![CDATA[flash]]></category>
		<category><![CDATA[share]]></category>
		<category><![CDATA[social]]></category>

		<guid isPermaLink="false">http://www.krotscheck.net/2009/12/21/how-to-publish-a-flash-application-to-the-facebook-stream.html</guid>
		<description><![CDATA[If you&#8217;re in an agency and/or have been paying attention to Business Week and the Wall Street Journal recently, you&#8217;ll know that my former employer Resource Interactive recently released a service offering called &#8220;Off The Wall&#8220;, which in short is a way to extend your e-commerce workflow into the Facebook stream. &#8220;Share on Facebook&#8221; can [...]]]></description>
			<content:encoded><![CDATA[<p>If you&#8217;re in an agency and/or have been paying attention to <a href="http://investing.businessweek.com/research/markets/news/article.asp?docKey=600-200910301156BIZWIRE_USPR_____BW5656-2QHHJKCOH16I2N0SL20B0UG0AN&amp;params=timestamp||10/30/2009%2011:56%20AM%20ET||headline||Resource%20Interactive%20Unveils%20Facebook%20Ecommerce%20Experience||docSource||Business%20Wire||provider||ACQUIREMEDIA" target="_blank">Business Week</a> and the <a href="http://blogs.wsj.com/digits/2009/12/21/shopping-comes-to-your-facebook-stream/" target="_blank">Wall Street Journal</a> recently, you&#8217;ll know that my former employer <a href="http://www.resource.com" target="_blank">Resource Interactive</a> recently released a service offering called &#8220;<a href="http://offthewall.resource.com/" target="_blank">Off The Wall</a>&#8220;, which in short is a way to extend your e-commerce workflow into the Facebook stream. &#8220;Share on Facebook&#8221; can now push a product to a user&#8217;s news feed, and if someone wants more information they never actually have to leave the Facebook environment to perform a &#8220;me too&#8221; purchase.</p>
<p>Cool, huhn? Security concerns aside (Believe me, I am never giving <i>anything</i> on facebook my credit card information), this isn&#8217;t exactly new- pushing product information into the Facebook stream was what the original <a href="http://en.wikipedia.org/wiki/Facebook_Beacon">Facebook Beacon</a> was all about, and that was shut down via a class action lawsuit because it published user sales data without user approval. Additionally, pushing rich media applications into the Facebook stream is not new- anyone who&#8217;s viewed a youtube video in their Facebook stream knows how seamless that can be. What&#8217;s interesting though is that Resource has overcome the legal concerns with two changes: First, by giving users control of what to share when, and secondly by actually launching a full commerce application into something that people check every day.</p>
<p>If your initial reaction is disgust (&#8220;What? Another way for people to sell us their stuff? Blegh&#8221;) then you and I are pretty much on the same page, however don&#8217;t be blinded by other creative uses of this. For instance, if you want to buy someone a Christmas present, wouldn&#8217;t it be nice if you saw their wishlist items in the stream? What about gaming- if a friend of yours is playing some kind of a live flash mini game&#8230; wouldn&#8217;t you want to join them immediately? There are legitimate uses for this that don&#8217;t turn your stomach, so I figured I&#8217;d write a quick overview on how to put it together.</p>
<h2>So how did they do that?</h2>
<p>If you already have an application you want to run inside the Facebook news stream, then the process of getting it shareable is extremely simple, and is easily accessible to anyone who knows a little bit about flash, HTML metadata and the facebook platform. You have to perform the following tasks, most of which are trivial unless you are trying to do anything covered by a regulatory body (like accepting credit card information). For that you have to have a secure and federally accredited server, and that&#8217;s way outside of the scope of this article.</p>
<h3>Step 1: Add the &#8220;Share on Facebook&#8221; link on the page in question.</h3>
<p>The first thing you need to do is give your users the ability to actually share your page. This can be as easy as <a href="http://www.facebook.com/facebook-widgets/share.php" target="_blank">including a particularly formatted link</a> in your product page or as complicated as including <a href="http://wiki.developers.facebook.com/index.php/Fb:share-button" target="_blank">FBML</a> in your site&#8217;s header and namespace. Note that the share URL can include URL parameters that will customize the content of the page, and should be pointed at the hosted URL of your flash application- this is crucial for step 2.</p>
<div class="code">
<pre>
&lt;a name="fb_share" type="button_count" href="http://www.facebook.com/sharer.php?u=[url to share]&amp;t=[title of content]"&gt;Share&lt;/a&gt;&lt;script src="http://static.ak.fbcdn.net/connect.php/js/FB.Share" type="text/javascript"&gt;&lt;/script&gt;
</pre>
</div>
<h3>Step 2: Add the correct meta tags to the page you want to share.</h3>
<p>When a user clicks on the above link, it actually triggers the Facebook Sharer script to scrape the provided URL for metadata that tells it how to share this page. All of this data is contained in the metadata tags of a page, and you can read the extensive documentation <a href="http://wiki.developers.facebook.com/index.php/Facebook_Share/Specifying_Meta_Tags" target="_blank">here</a>, however the important piece you&#8217;re looking for is how to share multimedia content. If you&#8217;ll read the documentation carefully, you&#8217;ll notice that while all references talk about video, in reality this share functionality allows you to display <i>any</i> flash content in the Facebook stream simply by replacing video_url with the URL to your flash SWF. This is still restricted to user action of course- nobody will see a flash app launched immediately, they&#8217;ll still see the icon and title as with any Youtube Video, and the application won&#8217;t launch until the user actually clicks on the icon.</p>
<div class="code">
<pre>
&lt;meta name="title" content="video_title" /&gt;
&lt;meta name="description" content="video_description" /&gt;
&lt;link rel="image_src" href="video_screenshot_image_src url" /&gt;
&lt;link rel="video_src" href="video_src url"/&gt;
&lt;meta name="video_height" content="video_height" /&gt;
&lt;meta name="video_width" content="video_width" /&gt;
&lt;meta name="video_type" content="application/x-shockwave-flash" /&gt;
</pre>
</div>
<p class="small"><span style="color: #BBBBBB; font-size: .8em">EDITORIALIZING: What worries me on this is that Facebook&#8217;s documentation is very clearly targeted at video sharing, and that this may be a violation of their intent of the sharer script. In short, what Resource is publishing as an innovation to social commerce is little more than a hack bolted into a loophole. Even so, I don&#8217;t believe Facebook will try to blacklist retailer sites to put this genie back in its bottle, because it both encourages use of their platform while also opening the gates to more legitimate uses. The ability to see that someone is, say, playing a game right now and your ability to join them is only a single click away puts an entire new spin on live online gaming, especially with the recent release of Adobe Collaboration Services, but I digress&#8230;</span></p>
<h3>Step 3: Get your domain whitelisted by Facebook</h3>
<p>If you paid especially close attention to the documentation linked above, you&#8217;ll also note that multimedia sharing won&#8217;t work if your domain is not whitelisted by Facebook. This is to protect Facebook from people who might want to distribute illegal content that would get them in trouble (licensed movies for instance), but also gives Facebook ultimate white and blacklist control over any activity they don&#8217;t want subverting their functionality. The process is actually extremely simple: <a href="http://www.facebook.com/developers/developer_help.php" target="_blank">Click this link</a>, fill out the form, and wait for them to get back to you. Last time I did it it took less than 24 hours, but that was for a major retail site; your experience might vary.</p>
<p>That&#8217;s it. Enjoy!</p>
]]></content:encoded>
			<wfw:commentRss>http://www.krotscheck.net/2009/12/21/how-to-publish-a-flash-application-to-the-facebook-stream.html/feed</wfw:commentRss>
		<slash:comments>6</slash:comments>
		</item>
	</channel>
</rss>

