Search code examples
iosswiftfacebookfacebook-ios-sdk

Facebook login not working in swift


Im trying to implement Facebook login in my app but when I try to login it goes to Facebook app and comes back to my game but the login button doesn't become log out and if I try to get any information such as access token, granted permissions or declined permissions it is nil. this is the code I have:

import Foundation
class IntroScene: SKScene, FBSDKLoginButtonDelegate {
let loginButton: FBSDKLoginButton = {
    let button = FBSDKLoginButton()
    button.readPermissions = ["email"]
    return button
}()

override func didMove(to view: SKView) {
    self.backgroundColor = UIColor.black

    view.addSubview(loginButton)
    loginButton.center = (self.view?.center)!
    loginButton.delegate = self
}

func loginButtonDidLogOut(_ loginButton: FBSDKLoginButton!) {

}

func loginButtonWillLogin(loginButton: FBSDKLoginButton!) -> Bool {
    return true
}

func loginButton(_ loginButton: FBSDKLoginButton!, didCompleteWith result: FBSDKLoginManagerLoginResult!, error: Error!) {
    if(error == nil)
    {
        print("login complete")
        //print(FBSDKAccessToken.current()) -> crashes because its nil
        //print(result.grantedPermissions) -> crashes its nil
    }
    else{
        print(error.localizedDescription)
    }
}
}

my info.plist looks like following:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
    <key>UIViewControllerBasedStatusBarAppearance</key>
    <false/>
    <key>LSApplicationQueriesSchemes</key>
    <array>
        <string>fbapi</string>
        <string>fb-messenger-api</string>
        <string>fbauth2</string>
        <string>fbshareextension</string>
    </array>
    <key>NSAppTransportSecurity</key>
    <dict>
        <key>NSExceptionDomains</key>
        <dict>
            <key>facebook.com</key>
            <dict>
                <key>NSIncludesSubdomains</key>
                <true/>
                <key>NSThirdPartyExceptionRequiresForwardSecrecy</key>
                <false/>
            </dict>
            <key>fbcdn.net</key>
            <dict>
                <key>NSIncludesSubdomains</key>
                <true/>
                <key>NSThirdPartyExceptionRequiresForwardSecrecy</key>
                <false/>
            </dict>
            <key>akamaihd.net</key>
            <dict>
                <key>NSIncludesSubdomains</key>
                <true/>
                <key>NSThirdPartyExceptionRequiresForwardSecrecy</key>
                <false/>
            </dict>
        </dict>
    </dict>
    <key>CFBundleURLTypes</key>
    <array>
        <dict>
            <key>CFBundleURLSchemes</key>
            <array>
            <string>//fbmyid</string>
        </array>
    </dict>
</array>
<key>FacebookAppID</key>
<string>//myid</string>
<key>FacebookDisplayName</key>
<string>Crazy Traffic Saga</string>
<key>CFBundleDevelopmentRegion</key>
<string>en</string>
<key>CFBundleExecutable</key>
<string>$(EXECUTABLE_NAME)</string>
<key>CFBundleIdentifier</key>
<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
<key>CFBundleInfoDictionaryVersion</key>
<string>6.0</string>
<key>CFBundleName</key>
<string>$(PRODUCT_NAME)</string>
<key>CFBundlePackageType</key>
<string>APPL</string>
<key>CFBundleShortVersionString</key>
<string>1.0</string>
<key>CFBundleSignature</key>
<string>????</string>
<key>CFBundleVersion</key>
<string>1</string>
<key>LSRequiresIPhoneOS</key>
<true/>
<key>UILaunchStoryboardName</key>
<string>LaunchScreen</string>
<key>UIMainStoryboardFile</key>
<string>Main</string>
<key>UIRequiredDeviceCapabilities</key>
<array>
    <string>armv7</string>
</array>
<key>UISupportedInterfaceOrientations</key>
<array>
    <string>UIInterfaceOrientationPortrait</string>
    <string>UIInterfaceOrientationLandscapeLeft</string>
    <string>UIInterfaceOrientationLandscapeRight</string>
</array>
<key>UISupportedInterfaceOrientations~ipad</key>
<array>
    <string>UIInterfaceOrientationPortrait</string>
    <string>UIInterfaceOrientationPortraitUpsideDown</string>
    <string>UIInterfaceOrientationLandscapeLeft</string>
    <string>UIInterfaceOrientationLandscapeRight</string>
</array>


Solution

  • Thanks to this post: FB Login using Swift 3 not returning any values and not get back the user to the App after successful login I found the problem. There is one more function that should be added to App Delegate. Here is how I got Facebook login working

    • Download SDK and add to project

    • Set up info.plist according to Facebook website

    • In app delegate added:

      func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
      // Override point for customization after application launch.
      FIRApp.configure()
      FBSDKApplicationDelegate.sharedInstance().application(application, didFinishLaunchingWithOptions: launchOptions)
      
      return true
      }
      
      public func application(_ app: UIApplication, open url: URL, options: [UIApplicationOpenURLOptionsKey : Any] = [:]) -> Bool {
      
          return FBSDKApplicationDelegate.sharedInstance().application(
              app,
              open: url as URL!,
              sourceApplication: options[UIApplicationOpenURLOptionsKey.sourceApplication] as! String,
          annotation: options[UIApplicationOpenURLOptionsKey.annotation]
      )
      }
      
      public func application(_ application: UIApplication, open url: URL,     sourceApplication: String?, annotation: Any) -> Bool {
              return FBSDKApplicationDelegate.sharedInstance().application(
                  application,
                  open: url as URL!,
                  sourceApplication: sourceApplication,
                  annotation: annotation)
      }
      
    • In the SKScene I'm showing the button (could be in a view controller as well):

      class IntroScene: SKScene, FBSDKLoginButtonDelegate {
          override func didMove(to view: SKView) {
              self.backgroundColor = UIColor.black
              let loginButton = FBSDKLoginButton()
              loginButton.center = (self.view?.center)!
              self.view?.addSubview(loginButton)
              loginButton.frame = CGRect(x: 0, y: 0, width: 360, height: 60) // makes it bigger
              loginButton.center = CGPoint(x: self.frame.midX, y: self.frame.midY + 90)
              loginButton.delegate = self
              loginButton.readPermissions = ["public_profile", "email"]
              if let _ = FBSDKAccessToken.current(){
                  //already logged in 
                  fetchProfile()
              }
          }
          func fetchProfile() {
          let parameters = ["fields": "first_name, email, last_name, picture"]
      
          FBSDKGraphRequest(graphPath: "me", parameters: parameters).start(completionHandler: { (connection, user, requestError) -> Void in
      
              if requestError != nil {
                  print("----------ERROR-----------")
                  print(requestError)
                  return
              }
              let userData = user as! NSDictionary
              let email = userData["email"] as? String
              let firstName = userData["first_name"] as? String
              let lastName = userData["last_name"] as? String
              var pictureUrl = ""
              if let picture = userData["picture"] as? NSDictionary, let data = picture["data"] as? NSDictionary, let url = data["url"] as? String {
                  pictureUrl = url
                  print(pictureUrl)
              }
           })
           }
      
      }