Dave Koziol
Dave Koziol

Reputation: 164

iOS TWTRComposer Request failed: unauthorized (401)

With the following code and a bunch of other variations I've tried, I always get an unauthorized error. I'm using TwitterKit 3.0 using CocoaPods. I've got my plist setup, my twitter app configured, and code like this:

// In didFinishLaunchingWithOptions
Twitter.sharedInstance().start(withConsumerKey:"XX", consumerSecret:"YYY")

func application(_ app: UIApplication, open url: URL, options: [UIApplicationOpenURLOptionsKey : Any] = [:]) -> Bool
{
    return Twitter.sharedInstance().application(app, open: url, options: options)
}

// In response to a click
Twitter.sharedInstance().logIn { session, error in
    if session != nil { // Log in succeeded
        let composer = TWTRComposer()

        composer.setText(tweetText)

        composer.show(from: self.navigationController!) { result in
            if (result == .done) {
                print("Successfully composed Tweet")
            } else {
                print("Cancelled composing")
            }
        }
    }
}

"Did encounter error sending Tweet: Error Domain=TWTRNetworkingErrorDomain Code=-1011 "Request failed: unauthorized (401)" UserInfo={NSLocalizedFailureReason=, TWTRNetworkingStatusCode=401, NSErrorFailingURLKey=https://api.twitter.com/1.1/statuses/update.json, NSLocalizedDescription=Request failed: unauthorized (401)"

Upvotes: 4

Views: 3828

Answers (4)

OhadM
OhadM

Reputation: 4803

In TwitterKit 3.3.0, basically:

Although the callback URL will not be requested by Twitter Kit in your app, it must be set to a valid URL for the app to work with the SDK.

even though when you try to create a Twitter app it doesn't say it is mandatory - which it is if you want below flow will work

Failing to do that will break below entire flow and nothing will happen automatically:

If Twitter is not installed on the device it automatically falls back to use OAuth via a web view (using SFSafariViewController for the first user, and a UIWebView for subsequent additional users.)

What will work if you won't have callback_url:

Only if the user has Twitter app installed we can compose a twit or log-in - the rest just doesn't work.

When Twitter app isn't installed:

  • When using composer.show(from: self) { (result) in you'll be getting .cancelled.
  • When using TWTRTwitter.sharedInstance().logIn(completion: { (session, error) in you'll be getting Request failed: unauthorized (401)

General notes:

  • If API key/secret are invalid, any action performed by TwitterKit lead to app crash

  • Ensure that the singleton start("key", "secret") method, and project plist with the value: twitterkit-{API KEY} has the same key or else your app will crash.

Upvotes: 0

dans
dans

Reputation: 23

If it doesn't work even after following Twitter's setup instructions, try regenerating the consumer keys. This fixed the problem for me.

Upvotes: 2

gamal
gamal

Reputation: 1665

I also face the same problem. I was using Twitter, FB and Google logins. the problem in the plist sequence of he URLSchemes

I added twitter Schemes first it worked

my ex -

 <key>CFBundleURLTypes</key>
        <array>
            <dict>
                <key>CFBundleURLSchemes</key>
                <array>
                    <string>twitterkit-xxxx</string>
                </array>
            </dict>
            <dict>
                <key>CFBundleURLSchemes</key>
                <array>
                    <string>fbxxxxx</string>
                </array>
            </dict>
            <dict>
                <key>CFBundleTypeRole</key>
                <string>Editor</string>
                <key>CFBundleURLSchemes</key>
                <array>
                    <string>com.googleusercontent.apps.xxxx-xxxx</string>
                </array>
            </dict>
        </array>

Upvotes: 0

Daniel Larsson
Daniel Larsson

Reputation: 6394

There is no reason to log in when using TWTRComposer. The SDK will use the current session in the Twitter App if there is one, or it will fall back in a smart way. I can't say why your login is failing, but I would suggest simply removing it to get around the problem.

let composer = TWTRComposer()

composer.setText(tweetText)

composer.show(from: self.navigationController!) { (result in
    if (result == .done) {
        print("Successfully composed Tweet")
    } else {
        print("Cancelled composing")
    }
}

You said that you already set everything up, but I will give you an installation checklist, should you have missed a step:

  • Initialize Twitter Kit

    func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
        Twitter.sharedInstance().start(withConsumerKey:"xxx", consumerSecret:"xxx")
    
        return true
     }
    
  • Configure Info.Plist

    // Info.plist
    <key>CFBundleURLTypes</key>
    <array>
      <dict>
        <key>CFBundleURLSchemes</key>
        <array>
          <string>twitterkit-<consumerKey></string>
        </array>
      </dict>
    </array>
    <key>LSApplicationQueriesSchemes</key>
    <array>
        <string>twitter</string>
        <string>twitterauth</string>
    </array>
    

If you are still having problems, make sure to check your app's status at https://apps.twitter.com/. There are multiple ways of getting your app key restricted or even deactivated. If this is the case, there will be a red label underneath the app name.

Upvotes: 0

Related Questions