diff --git a/LICENSE b/LICENSE
new file mode 100644
--- /dev/null
+++ b/LICENSE
@@ -0,0 +1,30 @@
+Copyright (c)2012, Felipe Lessa
+
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+
+    * Redistributions of source code must retain the above copyright
+      notice, this list of conditions and the following disclaimer.
+
+    * Redistributions in binary form must reproduce the above
+      copyright notice, this list of conditions and the following
+      disclaimer in the documentation and/or other materials provided
+      with the distribution.
+
+    * Neither the name of Felipe Lessa nor the names of other
+      contributors may be used to endorse or promote products derived
+      from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/README b/README
new file mode 100644
--- /dev/null
+++ b/README
diff --git a/Setup.hs b/Setup.hs
new file mode 100644
--- /dev/null
+++ b/Setup.hs
@@ -0,0 +1,2 @@
+import Distribution.Simple
+main = defaultMain
diff --git a/include/qq.h b/include/qq.h
new file mode 100644
--- /dev/null
+++ b/include/qq.h
@@ -0,0 +1,11 @@
+-- Stolen from yesod-auth.
+--
+-- CPP macro which choses which quasyquotes syntax to use depending
+-- on GHC version.
+--
+-- QQ stands for quasiquote.
+#if GHC7
+# define QQ(x) x
+#else
+# define QQ(x) $x
+#endif
diff --git a/src/Yesod/Auth/FB.hs b/src/Yesod/Auth/FB.hs
new file mode 100644
--- /dev/null
+++ b/src/Yesod/Auth/FB.hs
@@ -0,0 +1,142 @@
+module Yesod.Auth.FB
+    ( authFacebook
+    , facebookLogin
+    , facebookLogout
+    , getUserAccessToken
+    , setUserAccessToken
+    ) where
+
+#include "qq.h"
+import Control.Applicative ((<$>))
+import Control.Monad (when)
+import Control.Monad.IO.Class (MonadIO, liftIO)
+import Control.Monad.Trans.Class (lift)
+import Control.Monad.Trans.Maybe (MaybeT(..))
+import Data.Monoid (mappend)
+import Data.Text (Text)
+import Network.Wai (queryString)
+import Yesod.Auth
+import Yesod.Handler
+import Yesod.Widget
+import qualified Data.Text as T
+import qualified Data.Text.Encoding as TE
+import qualified Facebook as FB
+import qualified Network.HTTP.Conduit as H
+import qualified Yesod.Auth.Message as Msg
+
+
+-- | Route for login using this authentication plugin.
+facebookLogin :: AuthRoute
+facebookLogin = PluginR "fb" ["login"]
+
+
+-- | Route for logout using this authentication plugin.  At the
+-- time of writing, Facebook's policies
+-- (<https://developers.facebook.com/policy/>) specified that the
+-- user needs to be logged out from Facebook itself as well.
+facebookLogout :: AuthRoute
+facebookLogout = PluginR "fb" ["logout"]
+
+
+-- | Yesod authentication plugin using Facebook.
+authFacebook :: YesodAuth master
+             => FB.Credentials  -- ^ Your application's credentials.
+             -> H.Manager       -- ^ HTTP connection manager.
+             -> [FB.Permission] -- ^ Permissions to be requested.
+             -> AuthPlugin master
+authFacebook creds manager perms = AuthPlugin "fb" dispatch login
+  where
+    -- Get the URL in facebook.com where users are redirected to.
+    getRedirectUrl :: (YesodAuth master, Monad m) =>
+                      (Route Auth -> Route master)
+                   -> GGHandler sub master m Text
+    getRedirectUrl tm = do
+        render <- getUrlRender
+        let proceedUrl = render (tm proceedR)
+        return $ FB.getUserAccessTokenStep1 creds proceedUrl perms
+    proceedR = PluginR "fb" ["proceed"]
+
+    -- Redirect the user to Facebook.
+    dispatch "GET" ["login"] =
+        redirectText RedirectTemporary =<< getRedirectUrl =<< getRouteToMaster
+    -- Take Facebook's code and finish authentication.
+    dispatch "GET" ["proceed"] = do
+        tm     <- getRouteToMaster
+        render <- getUrlRender
+        query  <- queryString <$> waiRequest
+        let proceedUrl = render (tm proceedR)
+            query' = [(a,b) | (a, Just b) <- query]
+        token <- liftIO $
+                 FB.runFacebookT creds manager $
+                 FB.getUserAccessTokenStep2 proceedUrl query'
+        setUserAccessToken token
+        setCreds True (createCreds token)
+    -- Logout the user from our site and from Facebook.
+    dispatch "GET" ["logout"] = do
+        m      <- getYesod
+        tm     <- getRouteToMaster
+        mtoken <- getUserAccessToken
+        when (redirectToReferer m) setUltDestReferer
+
+        -- Facebook doesn't redirect back to our chosen address
+        -- when the user access token is invalid, so we need to
+        -- check its validity before anything else.
+        let isValid = liftIO .
+                      FB.runNoAuthFacebookT manager .
+                      FB.isValid
+        valid <- maybe (return False) isValid mtoken
+
+        case (valid, mtoken) of
+          (True, Just token) -> do
+            render <- getUrlRender
+            redirectText RedirectTemporary $
+              FB.getUserLogoutUrl token (render $ tm LogoutR)
+          _ -> redirect RedirectTemporary (tm LogoutR)
+    -- Anything else gives 404
+    dispatch _ _ = notFound
+
+    -- Small widget for multiple login websites.
+    login :: YesodAuth master =>
+             (Route Auth -> Route master)
+          -> GWidget sub master ()
+    login tm = do
+        redirectUrl <- lift (getRedirectUrl tm)
+        [QQ(whamlet)|
+<p>
+    <a href="#{redirectUrl}">_{Msg.Facebook}
+|]
+
+
+-- | Create an @yesod-auth@'s 'Creds' for a given
+-- @'FB.AccessToken' 'FB.User'@.
+createCreds :: FB.UserAccessToken -> Creds m
+createCreds (FB.UserAccessToken userId _ _) = Creds "fb" id_ []
+    where id_ = "http://graph.facebook.com/" `mappend` TE.decodeUtf8 userId
+
+
+-- | Set the Facebook's user access token on the user's session.
+-- Usually you don't need to call this function, but it may
+-- become handy together with 'FB.extendUserAccessToken'.
+setUserAccessToken :: MonadIO m =>
+                      FB.UserAccessToken
+                   -> GGHandler sub master m ()
+setUserAccessToken (FB.UserAccessToken userId data_ exptime) = do
+  setSession "_FBID" (TE.decodeUtf8 userId)
+  setSession "_FBAT" (TE.decodeUtf8 data_)
+  setSession "_FBET" (T.pack $ show exptime)
+
+
+-- | Get the Facebook's user access token from the session.
+-- Returns @Nothing@ if it's not found (probably because the user
+-- is not logged in via @yesod-auth-fb@).  Note that the returned
+-- access token may have expired, we recommend using
+-- 'FB.hasExpired' and 'FB.isValid'.
+getUserAccessToken :: MonadIO mo =>
+                      GGHandler sub master mo (Maybe FB.UserAccessToken)
+getUserAccessToken = runMaybeT $ do
+  userId  <- MaybeT $ lookupSession "_FBID"
+  data_   <- MaybeT $ lookupSession "_FBAT"
+  exptime <- MaybeT $ lookupSession "_FBET"
+  return $ FB.UserAccessToken (TE.encodeUtf8 userId)
+                              (TE.encodeUtf8 data_)
+                              (read $ T.unpack exptime)
diff --git a/yesod-auth-fb.cabal b/yesod-auth-fb.cabal
new file mode 100644
--- /dev/null
+++ b/yesod-auth-fb.cabal
@@ -0,0 +1,48 @@
+Name:                yesod-auth-fb
+Version:             0.0
+Synopsis:            [PREVIEW] Authentication backend for Yesod using Facebook.
+Homepage:            https://github.com/meteficha/yesod-auth-fb
+License:             BSD3
+License-file:        LICENSE
+Author:              Felipe Lessa, Michael Snoyman
+Maintainer:          Felipe Lessa <felipe.lessa@gmail.com>
+Category:            Web
+Build-type:          Simple
+Cabal-version:       >= 1.6
+Extra-source-files:  include/qq.h, README
+
+Description:
+  /THIS IS A PREVIEW RELEASE!/
+  .
+  This package allows you to use Yesod's authentication framework
+  with Facebook as your backend.  That is, your site's users will
+  log in to your site through Facebook.  Your application need to
+  be registered on Facebook.
+
+Source-repository head
+  type:     git
+  location: git://github.com/meteficha/yesod-auth-fb.git
+
+flag ghc7
+
+Library
+  hs-source-dirs: src
+
+  if flag(ghc7)
+    Cpp-options:   -DGHC7
+    Build-depends: base         >= 4.3     && < 5
+  else
+    Build-depends: base         >= 4       && < 4.3
+
+  Build-depends:   yesod-core   >= 0.9     && < 0.10
+                 , yesod-auth   >= 0.7     && < 0.8
+                 , wai
+                 , http-conduit
+                 , text         >= 0.7     && < 0.12
+                 , transformers >= 0.1.3   && < 0.3
+                 , fb           >= 0.6.0.1 && < 0.7
+
+  Exposed-modules: Yesod.Auth.FB
+  Extensions: GADTs QuasiQuotes CPP OverloadedStrings
+  GHC-options: -Wall
+  Include-dirs: include
