[TUT] Sending a Tweet

By blundell  

Implemented this myself so thought I would share.
This isn’t the prettiest solution but it gives you all the facts and is nice an quick.
I’ve kept it all in one Activity to try and give you the overview you can deal with the OO later yourself.

Source file downloads are at the bottom of this post.

Ok What we are going to do:

Authorise your app to use a users twitter account.
Send a tweet from this account.

Workflow:

User presses Login Button
Checks if user has logged in before
Twitter webpage is opened
User logins in to twitter
App is then allowed to post tweets
Users presses Tweet Button
Tweet is sent to Twitter
Simple!

A sneak preview of what it’ll look like:

Setup:

You need to create a Twitter Application (takes 2 mins) on the Twitter site: https://dev.twitter.com/apps/

Just like this :
twitter create settings

Ensure
Application Type: Browser
Permissions: Read & Write
Callback URL; doesnt matter put anything http://google.com

Next you need the Twitter4j Jar, this does all the hard work behind the scenes.

You can download it here: Twitter4J jar

Unzip it.
You then have to add it to your project.

Eclipse:
Right Click on your project > Properties > Java Build Path > Add External Jars > twitter4j-core-android-2.2.3.jar> OK

Easy!

Ok now to the coding!

First your manifest needs to be able to receive the twitter call back from the browser, it also needs the activity to be single instance:

<?xml version="1.0" encoding="utf-8"?>
<manifest
        xmlns:android="http://schemas.android.com/apk/res/android"
        package="com.blundell.tut.ttt"
        android:versionCode="1"
        android:versionName="1.0">
        <uses-sdk
                android:minSdkVersion="4" />
 
        <!-- used by twitter integration -->
        <uses-permission
                android:name="android.permission.INTERNET" />
 
        <application
                android:icon="@drawable/icon"
                android:label="@string/app_name">
                <activity
                        android:name=".TweetToTwitterActivity"
                        android:label="@string/app_name"
                        android:launchMode="singleInstance">
                        <intent-filter>
                                <action android:name="android.intent.action.MAIN" />
                                <category android:name="android.intent.category.LAUNCHER" />
                        </intent-filter>
                        <intent-filter>
                                <action android:name="android.intent.action.VIEW" />
                                <category android:name="android.intent.category.DEFAULT" />
                                <category android:name="android.intent.category.BROWSABLE" />
                                <data android:scheme="tweet-to-twitter-blundell-01-android" />
                        </intent-filter>
                </activity>
 
        </application>
</manifest>

Then I’ve compacted it all into a single Activity with comments so you should be able to understand what is going on:

package com.blundell.tut.ttt;
 
import twitter4j.Twitter;
import twitter4j.TwitterException;
import twitter4j.TwitterFactory;
import twitter4j.auth.AccessToken;
import twitter4j.auth.RequestToken;
import android.app.Activity;
import android.content.Intent;
import android.content.SharedPreferences;
import android.content.SharedPreferences.Editor;
import android.net.Uri;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.webkit.WebView;
import android.widget.Button;
import android.widget.Toast;
 
public class TweetToTwitterActivity extends Activity {
 
        private static final String TAG = "Blundell.TweetToTwitterActivity";
 
        /** Name to store the users access token */
        private static final String PREF_ACCESS_TOKEN = "accessToken";
        /** Name to store the users access token secret */
        private static final String PREF_ACCESS_TOKEN_SECRET = "accessTokenSecret";
        /** Consumer Key generated when you registered your app at https://dev.twitter.com/apps/ */
        private static final String CONSUMER_KEY = "yourConsumerKey";
        /** Consumer Secret generated when you registered your app at https://dev.twitter.com/apps/  */
        private static final String CONSUMER_SECRET = "yourConsumerSecret"; // XXX Encode in your app
        /** The url that Twitter will redirect to after a user log's in - this will be picked up by your app manifest and redirected into this activity */
        private static final String CALLBACK_URL = "tweet-to-twitter-blundell-01-android:///";
        /** Preferences to store a logged in users credentials */
        private SharedPreferences mPrefs;
        /** Twitter4j object */
        private Twitter mTwitter;
        /** The request token signifies the unique ID of the request you are sending to twitter  */
        private RequestToken mReqToken;
 
        private Button mLoginButton;
        private Button mTweetButton;
 
        /** Called when the activity is first created. */
        @Override
        public void onCreate(Bundle savedInstanceState) {
                super.onCreate(savedInstanceState);
                Log.i(TAG, "Loading TweetToTwitterActivity");
                setContentView(R.layout.main);
               
                // Create a new shared preference object to remember if the user has
                // already given us permission
                mPrefs = getSharedPreferences("twitterPrefs", MODE_PRIVATE);
                Log.i(TAG, "Got Preferences");
               
                // Load the twitter4j helper
                mTwitter = new TwitterFactory().getInstance();
                Log.i(TAG, "Got Twitter4j");
               
                // Tell twitter4j that we want to use it with our app
                mTwitter.setOAuthConsumer(CONSUMER_KEY, CONSUMER_SECRET);
                Log.i(TAG, "Inflated Twitter4j");
               
                mLoginButton = (Button) findViewById(R.id.login_button);
                mTweetButton = (Button) findViewById(R.id.tweet_button);
        }
 
        /**
         * Button clickables are declared in XML as this projects min SDK is 1.6</br> </br>
         * Checks if the user has given this app permission to use twitter
         * before</br> If so login and enable tweeting</br>
         * Otherwise redirect to Twitter for permission
         *
         * @param v the clicked button
         */
        public void buttonLogin(View v) {
                Log.i(TAG, "Login Pressed");
                if (mPrefs.contains(PREF_ACCESS_TOKEN)) {
                        Log.i(TAG, "Repeat User");
                        loginAuthorisedUser();
                } else {
                        Log.i(TAG, "New User");
                        loginNewUser();
                }
        }
 
        /**
         * Button clickables are declared in XML as this projects min SDK is 1.6</br> </br>
         *
         * @param v the clicked button
         */
        public void buttonTweet(View v) {
                Log.i(TAG, "Tweet Pressed");
                tweetMessage();
        }
 
        /**
         * Create a request that is sent to Twitter asking 'can our app have permission to use Twitter for this user'</br>
         * We are given back the {@link mReqToken}
         * that is a unique indetifier to this request</br>
         * The browser then pops up on the twitter website and the user logins in ( we never see this informaton
         * )</br> Twitter then redirects us to {@link CALLBACK_URL} if the login was a success</br>
         *
         */
        private void loginNewUser() {
                try {
                        Log.i(TAG, "Request App Authentication");
                        mReqToken = mTwitter.getOAuthRequestToken(CALLBACK_URL);
 
                        Log.i(TAG, "Starting Webview to login to twitter");
                        WebView twitterSite = new WebView(this);
                        twitterSite.loadUrl(mReqToken.getAuthenticationURL());
                        setContentView(twitterSite);
 
                } catch (TwitterException e) {
                        Toast.makeText(this, "Twitter Login error, try again later", Toast.LENGTH_SHORT).show();
                }
        }
 
        /**
         * The user had previously given our app permission to use Twitter</br>
         * Therefore we retrieve these credentials and fill out the Twitter4j helper
         */
        private void loginAuthorisedUser() {
                String token = mPrefs.getString(PREF_ACCESS_TOKEN, null);
                String secret = mPrefs.getString(PREF_ACCESS_TOKEN_SECRET, null);
 
                // Create the twitter access token from the credentials we got previously
                AccessToken at = new AccessToken(token, secret);
 
                mTwitter.setOAuthAccessToken(at);
               
                Toast.makeText(this, "Welcome back", Toast.LENGTH_SHORT).show();
               
                enableTweetButton();
        }
 
        /**
         * Catch when Twitter redirects back to our {@link CALLBACK_URL}</br>
         * We use onNewIntent as in our manifest we have singleInstance="true" if we did not the
         * getOAuthAccessToken() call would fail
         */
        @Override
        protected void onNewIntent(Intent intent) {
                super.onNewIntent(intent);
                Log.i(TAG, "New Intent Arrived");
                dealWithTwitterResponse(intent);
        }
 
        @Override
        protected void onResume() {
                super.onResume();
                Log.i(TAG, "Arrived at onResume");
        }
       
        /**
         * Twitter has sent us back into our app</br>
         * Within the intent it set back we have a 'key' we can use to authenticate the user
         *
         * @param intent
         */
        private void dealWithTwitterResponse(Intent intent) {
                Uri uri = intent.getData();
                if (uri != null && uri.toString().startsWith(CALLBACK_URL)) { // If the user has just logged in
                        String oauthVerifier = uri.getQueryParameter("oauth_verifier");
 
                        authoriseNewUser(oauthVerifier);
                }
        }
 
        /**
         * Create an access token for this new user</br>
         * Fill out the Twitter4j helper</br>
         * And save these credentials so we can log the user straight in next time
         *
         * @param oauthVerifier
         */
        private void authoriseNewUser(String oauthVerifier) {
                try {
                        AccessToken at = mTwitter.getOAuthAccessToken(mReqToken, oauthVerifier);
                        mTwitter.setOAuthAccessToken(at);
 
                        saveAccessToken(at);
 
                        // Set the content view back after we changed to a webview
                        setContentView(R.layout.main);
                       
                        enableTweetButton();
                } catch (TwitterException e) {
                        Toast.makeText(this, "Twitter auth error x01, try again later", Toast.LENGTH_SHORT).show();
                }
        }
 
        /**
         * Allow the user to Tweet
         */
        private void enableTweetButton() {
                Log.i(TAG, "User logged in - allowing to tweet");
                mLoginButton.setEnabled(false);
                mTweetButton.setEnabled(true);
        }
 
        /**
         * Send a tweet on your timeline, with a Toast msg for success or failure
         */
        private void tweetMessage() {
                try {
                        mTwitter.updateStatus("Test - Tweeting with @Blundell_apps #AndroidDev Tutorial using #Twitter4j http://blog.blundell-apps.com/sending-a-tweet");
 
                        Toast.makeText(this, "Tweet Successful!", Toast.LENGTH_SHORT).show();
                } catch (TwitterException e) {
                        Toast.makeText(this, "Tweet error, try again later", Toast.LENGTH_SHORT).show();
                }
        }
 
        private void saveAccessToken(AccessToken at) {
                String token = at.getToken();
                String secret = at.getTokenSecret();
                Editor editor = mPrefs.edit();
                editor.putString(PREF_ACCESS_TOKEN, token);
                editor.putString(PREF_ACCESS_TOKEN_SECRET, secret);
                editor.commit();
        }
}

If you find this helpful please say thanks :-) Happy Coding

And any questions just ask!

The eclipse project src as promised:

—> TweetToTwitter <---


100 Comments

  1. bhavesh
    Posted February 15, 2014 at 1:11 pm | Permalink | Reply

    I am getting “Twitter Login error, try again later”. In my case it’s giving me problem in this line.
    mReqToken = mTwitter.getOAuthRequestToken(CALLBACK_URL);

    It’s crashing from here. it directly goes to catch didn’t even execute the webview part. I found this may be because of wrong time in device. But I double checked that’s not a problem. Cay any one guide me what could be issue behind this?

    Thanks in advance.

  2. vince
    Posted November 14, 2013 at 2:05 pm | Permalink | Reply

    HI ! I’ve followed your code, and it works! But i have a problem: I want that after the Twitter name/passw step,instead of returning to the mainActivity, I need to go to another Activity…how can I do that?
    Thanks in advance!

    • blundell
      Posted December 7, 2013 at 10:09 pm | Permalink | Reply

      I believe you just need to edit the intent filter in your AndroidMAnifest

  3. nikola
    Posted September 16, 2013 at 12:35 pm | Permalink | Reply

    thanks million times. This works perfectly.

  4. Thailey
    Posted September 8, 2013 at 9:09 pm | Permalink | Reply

    Thank you for the insight and excellent commenting on the code to a very confusing task. My question is about what happens when you sign-in to your twitter account for the first time. It takes me to the Authorize page and I hit sign in but it doesn’t do anything after that. If I hit cancel it takes me back to the app as it’s supposed to but I can’t seem to authorize as needed. Also when I first tried to run this I had to create a new thread in order to run mTwitter.getOAuthRequestToken(CALLBACK_URL); because it said you couldn’t run this on main thread. Thank you for your time

    • blundell
      Posted September 15, 2013 at 11:24 am | Permalink | Reply

      Hi sorry Thailey this tutorial is out of date and Twitter has now changed its API :-(

  5. Ranjith sankar
    Posted August 13, 2013 at 12:28 pm | Permalink | Reply

    hi frnd,

    i use your code in my application and it works successfully till the login process. and now the problem is that after successfull login the code which i written in newIntent() method is not working…. why this happen pls help me..

  6. Waleed
    Posted July 10, 2013 at 9:22 pm | Permalink | Reply

    i want to send image using app instead of status

  7. joseBallester
    Posted June 28, 2013 at 4:59 pm | Permalink | Reply

    I have a problem with the application open the page of twitter but when I put the user and password do not direct to the application, Instead direction to the callback_url and the application does nothing more.

    • joseBallester
      Posted June 28, 2013 at 9:49 pm | Permalink | Reply

      Hi a solve this problem I just erase “Callback URL” in twitter developers. Now I have the problem whit a PIN code. anybody have an idea.

      • Ranjith sankar
        Posted August 13, 2013 at 12:29 pm | Permalink | Reply

        ur onNewIntent() method works fine or not??

  8. Ugur
    Posted June 23, 2013 at 4:52 pm | Permalink | Reply

    ok now i debugged and found the problem.
    it’s twitter api v1 cause i gives this error:
    “The Twitter REST API v1 is no longer active”

    How can i switch to twitter API v1.1?

    • blundell
      Posted June 28, 2013 at 10:06 pm | Permalink | Reply

      nooo, I haven’t checked this in a while, silly twitter!

  9. Ugur
    Posted June 23, 2013 at 11:13 am | Permalink | Reply

    Hi,
    I’ve found your example a couple months ago, i entegreted it with my app nad it has been working perfectly till now.
    I havent changed anything.But when i click tweet button it throws exeption at this part:
    private void tweetMessage() {
    try {
    //mTwitter.updateStatus(“Test2 – #AndroidDev”);
    Toast.makeText(this, “Tweeted Successfully!”, Toast.LENGTH_SHORT).show();
    finish();

    } catch (TwitterException e) {
    Toast.makeText(this, “Tweet error, try again later.”, Toast.LENGTH_SHORT).show(); }
    }
    }
    I donwloaded your project again and it’s gave the same error.I created a new app and user but it doesnt work.
    What should i do?
    Is it because twitter api v.1.1 or something?

    Please help.Thank you

    • blundell
      Posted June 28, 2013 at 10:07 pm | Permalink | Reply

      Yeah, I’ll need to update my TUT thanks for the heads up

  10. Wazby
    Posted June 16, 2013 at 7:53 pm | Permalink | Reply

    Hello,i have question i’ve tried implementing your code imported it like a project from existing code, thelogin seems to work but when i come back from the authentication ,the tweet button is not enabled, might you know what could be the problem or maybe i am doing something wrong? Thanks in advance.

    • blundell
      Posted June 28, 2013 at 10:09 pm | Permalink | Reply

      think the api has been deprecated :-(

  11. zxsteve
    Posted April 25, 2013 at 3:36 am | Permalink | Reply

    Hello,
    Program working brilliantly, posted to Twitter first time, please can you tell me how I can incorporate this into my existing application? Is there a class that you can create from this app that I can call from my main app?

    Cheers

    • blundell
      Posted April 28, 2013 at 3:49 pm | Permalink | Reply

      Yeah you can just create this as your TwitterActivity and start it with an Intent

  12. Sumit
    Posted February 25, 2013 at 9:48 am | Permalink | Reply

    Thanks man ….. nice tutorial

  13. Bikash
    Posted February 22, 2013 at 7:47 pm | Permalink | Reply

    Hi thanks for tutorials, I am new to android, I have tried your code but it showing me problem with login, it is showing me toast at line 116.

    Could you please help me to solve this it’s very urgent.

  14. ajay
    Posted February 22, 2013 at 2:55 pm | Permalink | Reply

    Hi, i changed consumer key and consumer secrete key but i am still getting error in your project. and error is -
    java.lang.VerifyError: com.blundell.tut.ttt.TweetToTwitterActivity
    where as i have put all keys correctly. and also check for second project but getting same error. so please tell me what the problem is exactly.
    and i also don’t find field application type(client , browser) on dev.twitter.com web site. so please help.

  15. Carl
    Posted February 5, 2013 at 2:20 am | Permalink | Reply

    Thank you very much for this tutorial. Good Job.

  16. Robert
    Posted January 16, 2013 at 4:09 am | Permalink | Reply

    It’s useful, thanks a lot.

  17. vijeta
    Posted January 4, 2013 at 6:22 am | Permalink | Reply

    I have followed the procedure completely, included all the libraries. Still i am getting this error:
    01-04 11:48:58.016: E/dalvikvm(328): Could not find class ‘twitter4j.http.AccessToken’, referenced from method com.ecs.android.sample.twitter.TwitterUtils.isAuthenticated
    01-04 11:48:58.067: E/AndroidRuntime(328): java.lang.NoClassDefFoundError: twitter4j.http.AccessToken
    01-04 11:48:58.067: E/AndroidRuntime(328): at com.ecs.android.sample.twitter.TwitterUtils.isAuthenticated(TwitterUtils.java:18)
    01-04 11:48:58.067: E/AndroidRuntime(328): at com.ecs.android.sample.twitter.AndroidTwitterSample.updateLoginStatus(AndroidTwitterSample.java:72)
    01-04 11:48:58.067: E/AndroidRuntime(328): at com.ecs.android.sample.twitter.AndroidTwitterSample.onResume(AndroidTwitterSample.java:68)

    • blundell
      Posted January 4, 2013 at 9:36 am | Permalink | Reply

      Somethings wrong with your classpath, you need to export the twitter4j jar with your app when it is deployed

  18. MASK
    Posted December 28, 2012 at 7:40 pm | Permalink | Reply

    Thanks!! Great work!

  19. alpha2
    Posted December 12, 2012 at 2:16 am | Permalink | Reply

    Thanks a lot for the tutorial. Twitter4j really lacks android example.
    This is very helpful.

  20. Posted November 8, 2012 at 1:13 pm | Permalink | Reply

    Its like you read my mind! You appear to know a lot approximately this, such as you wrote the guide in it or something. A fantastic read.

    I’ll certainly be back.

  21. Tuba
    Posted October 31, 2012 at 12:50 pm | Permalink | Reply

    H? I want to post tweet from android phone When I go to https://dev.twitter.com/apps/ page , I don’t see Application Type. So, The application give me error

  22. alvin
    Posted October 31, 2012 at 10:15 am | Permalink | Reply

    hi I tried your sourcecode above but I got this error when I run it to my nexus s.

    10-31 18:12:15.699: E/AndroidRuntime(7881): FATAL EXCEPTION: main
    10-31 18:12:15.699: E/AndroidRuntime(7881): java.lang.VerifyError: edu/rivera/augmentwit/MainActivity
    10-31 18:12:15.699: E/AndroidRuntime(7881): at java.lang.Class.newInstanceImpl(Native Method)
    10-31 18:12:15.699: E/AndroidRuntime(7881): at java.lang.Class.newInstance(Class.java:1319)
    10-31 18:12:15.699: E/AndroidRuntime(7881): at android.app.Instrumentation.newActivity(Instrumentation.java:1053)

    • blundell
      Posted November 1, 2012 at 9:31 am | Permalink | Reply

      Hmm verify error is something like the app didn’t install correctly, or class declarations are incorrect, i.e. AndroidManifest or packages. The source code works!

  23. Tikam
    Posted October 29, 2012 at 7:11 am | Permalink | Reply

    Dear Blundell,

    Its working fine for me.

    How can we implement whole process with help of WebView, Please explain wholw process to implement it.

  24. Tikam
    Posted October 29, 2012 at 7:07 am | Permalink | Reply

    Dear Blundell,

    Great tutorial,
    I am able to tweet my custom tweet from above program.

    How Can it will be implement whole process with help of WebView?

  25. AB
    Posted October 28, 2012 at 5:46 pm | Permalink | Reply

    Hello blundell,
    Nice blog ..!!really helpful in getting started..!!
    The only issue is every time i get registered as a new user.
    so here is how it should have worked according to code,u first click on login button for the first time,then registers with twitter,then comes back to the activity,tweet button should be enabled..have i done it rightly??
    also now if i press login button i should be detected as a “repeat user” and should be able to tweet..either ways all what is happening is i am just getting registered,i am not able to go back to the screen and tweet..can u help me get it right??

    • blundell
      Posted October 29, 2012 at 1:19 pm | Permalink | Reply

      There is no registration involved, perhaps take a second look at how you are signing in.

  26. Posted October 26, 2012 at 3:46 pm | Permalink | Reply

    This was an extremely helpful post. Probably the first complete *and working* example of Twitter OAuth in an Android app.

    Thank you very much!

  27. Posted October 11, 2012 at 1:15 pm | Permalink | Reply

    There is no action on the button when i pressed them, please help me out. Thanks

    • blundell
      Posted October 11, 2012 at 1:58 pm | Permalink | Reply

      Hi UI check you have set your onClickListeners correctly, or have it defined in the XML layout file

  28. swapnil
    Posted September 5, 2012 at 9:07 am | Permalink | Reply

    hey thanks for tutorial
    see i have used your code but on ics and jellybean it shows fouce close when you press login button…
    I want to develop app in which user can twitte that XYZ listening XYZ file on XYZ app..
    Also I want to show recent twits made by other member .
    can you help me
    thank you

    • blundell
      Posted September 13, 2012 at 7:23 am | Permalink | Reply

      Hi you’ll have to move the networking code into its own Thread.

  29. Posted August 1, 2012 at 2:52 pm | Permalink | Reply

    Hi Blundell, I have a really strange error, on my app, when the log in screen comes with the permissions requiered by the app, it doesn’t let me put my username or password? any idea what could it be?

    • blundell
      Posted August 2, 2012 at 7:00 am | Permalink | Reply

      H,, are they loading into a webview and it needs to set javascript enabled? Otherwise it’s a browser issue

  30. Posted July 18, 2012 at 8:41 am | Permalink | Reply

    how can i perform the same task in the tabHost?? when i click on the sing-in button on the web browser it gives the error “android.view.WindowManager$BadTokenException: Unable to add window — token android.app.LocalActivityManager$LocalActivityRecord@40e038c0 is not valid; is your activity running?”

    in the tabhost the tweet part it in the child activity.. please help me out..!!
    Thanks in advance..!!

    • blundell
      Posted July 19, 2012 at 8:03 pm | Permalink | Reply

      Hi sorry I don’t have experience of using a WebView inside of a TabHost, I don’t see an immediate problem. Perhaps try it outside of the tabhost first to ensure you can get it to work with your project, then move it inside.

  31. Sleepy
    Posted July 17, 2012 at 6:17 pm | Permalink | Reply

    I’m receiving a weird bug – after logging in and out successfully once using some modified methods from this post, the callback URL twitter sends back is http://api.twitter.commy-callback-url.my-domain.com/etc

    Just like that, no space or slash, as if my callback url was directly appended on to the twitter api url.

    I’m stumped for ideas, I’d appreciate any help

    • blundell
      Posted July 18, 2012 at 7:19 am | Permalink | Reply

      Hmm that is strange. Maybe try writing a question on StackOverflow with a simple case to reproduce it. I’m sure you’ll get a fair bit of attention

    • Ivo
      Posted July 30, 2012 at 1:54 pm | Permalink | Reply

      i had the same problem. I fixed it by removing all cookies on logout.
      I eventually used this as my logout function:

      public void logout() {
      Editor editor = mPrefs.edit();
      editor.remove(PREF_ACCESS_TOKEN);
      editor.commit();
      mTwitter.setOAuthAccessToken(null);
      CookieSyncManager.createInstance(activity);
      CookieManager.getInstance().removeAllCookie();
      }

  32. fjr619
    Posted July 12, 2012 at 10:38 am | Permalink | Reply

    why when i finished login it is not direct again to app but direct to callback url so when i finished login direct to webpage url

  33. Eric
    Posted June 24, 2012 at 8:42 pm | Permalink | Reply

    How would you set this up using Async Task? Every time I try and log in, I get a NetworkOnMainThreadException. Is Async the thing to use here? I am having a hard time implementing it into the code though.

    • blundell
      Posted June 25, 2012 at 10:15 am | Permalink | Reply

      Hi Eric,
      This tutorial uses a webview so I don’t see what networking you are doing. You must be doing something outside the tut. but yes you shouldn’t do internet calls on your UI thread, use a background thread or an ASyncTask

      • Eric
        Posted June 26, 2012 at 2:42 pm | Permalink | Reply

        Well, when I try and run the app on ICS, it force closes because it’s running in the main thread. So I try and use Async Task, but it won’t let me set up the WebView for some reason..

      • Eric
        Posted June 26, 2012 at 10:36 pm | Permalink | Reply

        Oh, and the method that is crashing is loginNewUser

        • Silke
          Posted June 27, 2012 at 11:24 pm | Permalink | Reply

          ditto to that problem :) should take off the main thread for ICS – awesome tutorial blundell! Thanks for being a legend and commenting

          • swapnil
            Posted September 5, 2012 at 2:27 pm | Permalink

            what do u mean by take off main thread…i dont get it can you please explain me

          • Doug123_2
            Posted June 8, 2013 at 12:01 pm | Permalink

            Yes, I totally agree with Silke: Commenting in sample Java apps, especially for Android, is so rare. Proper commenting can make soooo much difference to the readability of code, not just for others, but for your own maintenance later, when you’re trying to work out why you wrote the code that way in the first place!

            Well done Blundell!

  34. Matt
    Posted June 11, 2012 at 7:00 am | Permalink | Reply

    Hi, thanks for sharing. I’m trying to adapt this to an app where the Twitter portion is in it’s own Intent/Activity.

    As is, I’m getting a VerifyError exception, it seems to be failing (as noted in the article) on the OAuthAccessToken call. I’m not sure exactly how to fix this (kind of a noob here). Obviously I’ll need to do some doctoring on my manifest, but that’s a bit beyond me at the moment.

    Here’s what LogCat has to say:

    
    06-11 01:43:20.975: I/dalvikvm(5985): Could not find method twitter4j.Twitter.getOAuthAccessToken, referenced from method ***.IntegrateTwitter.authoriseNewUser
    06-11 01:43:20.975: W/dalvikvm(5985): VFY: unable to resolve interface method 359: Ltwitter4j/Twitter;.getOAuthAccessToken (Ltwitter4j/auth/RequestToken;Ljava/lang/String;)Ltwitter4j/auth/AccessToken;
    06-11 01:43:20.990: W/dalvikvm(5985): VFY: unable to resolve exception class 144 (Ltwitter4j/TwitterException;)
    06-11 01:43:20.990: W/dalvikvm(5985): VFY:  rejected L***/IntegrateTwitter;.authoriseNewUser (Ljava/lang/String;)V
    06-11 01:43:20.990: W/dalvikvm(5985): VFY:  rejected L***/IntegrateTwitter;.authoriseNewUser (Ljava/lang/String;)V
    06-11 01:43:20.990: W/dalvikvm(5985): Verifier rejected class L***/IntegrateTwitter;
    06-11 01:43:20.990: W/dalvikvm(5985): Class init failed in newInstance call (L***/IntegrateTwitter;)
    06-11 01:43:20.990: E/AndroidRuntime(5985): java.lang.VerifyError: ***.IntegrateTwitter
    

    Could you give me any hints or a direction to go with debugging? Thanks again.

    • blundell
      Posted June 11, 2012 at 11:50 am | Permalink | Reply

      Ooo not too sure about this error, make sure your using the same twitter4j.jar that the tutorial uses, ensure it is added to your manifest correctly. It seems it’s something to do with twitter4j itself

    • Sark
      Posted June 24, 2012 at 9:06 pm | Permalink | Reply

      Hello Matt,

      I am getting the similar error

      Could not find method twitter4j.Twitter.getOAuthAccessToken,

      How did you solve the problem?

      Thanks.

      • Matt
        Posted June 29, 2012 at 12:52 am | Permalink | Reply

        I’ve since heavily modified this example, so I’m not entirely sure, but as I recall, one of my problems was that the twitter4j library was not being used as a library properly.

        Go to your project properties -> Java Build Path -> Order and Export tab, and ensure the box next to the twitter4j JAR is checked.

  35. mainder
    Posted June 8, 2012 at 12:56 am | Permalink | Reply

    Your code works (Thanks btw) but when I get to the twitter login web view it doesn’t display the keyboard when I click. I’m pretty sure it has nothing to do with your stuff but, any suggestions what can it be??

    • blundell
      Posted June 8, 2012 at 12:22 pm | Permalink | Reply

      Thanks, well done! Hmm I’ve seen issue’s like this before, if you open it in a webview there are a couple of things you can do with enabling javascript (check stackoverflow), but if it is just opening the browser sorry the keyboard opening will just phone dependant. :-(

      • mainder
        Posted June 8, 2012 at 9:09 pm | Permalink | Reply

        Solved! It’s a bug from Android untill version 2.1 I think. In case somebody has the same problem, the solution is this here. Thanks for the tutorial!

        http://stackoverflow.com/questions/3460915/webview-textarea-doesnt-pop-up-the-keyboard

        • afritz
          Posted June 9, 2012 at 4:47 pm | Permalink | Reply

          @mainder, how you fix the code?

          I tried, but still the keyboard doesn’t show up..

          can you share your code?

          • mainder
            Posted June 9, 2012 at 7:34 pm | Permalink

            private void loginNewUser() {
            try {
            Log.i(TAG, “Request App Authentication”);
            mReqToken = mTwitter.getOAuthRequestToken(CALLBACK_URL);

            Log.i(TAG, “Starting Webview to login to twitter”);
            WebView twitterSite = new WebView(this);
            twitterSite.requestFocus(View.FOCUS_DOWN);
            twitterSite.setOnTouchListener(new View.OnTouchListener() {
            @Override
            public boolean onTouch(View v, MotionEvent event) {
            switch (event.getAction()) {
            case MotionEvent.ACTION_DOWN:
            case MotionEvent.ACTION_UP:
            if (!v.hasFocus()) {
            v.requestFocus();
            }
            break;
            }
            return false;
            }
            });
            twitterSite.loadUrl(mReqToken.getAuthenticationURL());
            setContentView(twitterSite);

            } catch (TwitterException e) {
            Toast.makeText(this, “Twitter Login error, try again later”,
            Toast.LENGTH_SHORT).show();

            }
            }

          • afritz
            Posted June 10, 2012 at 2:50 am | Permalink

            @minder… thank you very much… it’s working now.. :)

  36. Catherine
    Posted June 4, 2012 at 11:58 am | Permalink | Reply

    Thanks for this, been trying to write a Android Twitter App and kept getting java.lang.NoClassDefFoundError: twitter4j.TwitterFactory

    I compared you code with mine and couldn’t see anything I was doing wrong and i’d imported the twitter4j libraries correctly. I did notice that you were using version 2.2.3-1 and I was using 2.2.5 so I swapped to 2.2.3-1 and found my code was now working ok.
    So just wondering if you had come across the same problem given that as far as I can tell 2.2.5 was already out when you wrote this tutorial?

    • blundell
      Posted June 5, 2012 at 8:50 am | Permalink | Reply

      Interesting, no I didn’t come across it, I don’t think 2.2.5 was out when I wrote this but if it was I was just lucky and had the older version downloaded!

  37. Posted June 2, 2012 at 7:11 am | Permalink | Reply

    Hi blundell..I done as step as you write above.But it also as weeber error : “Twitter Login error, try again later”..I look logcat and display error: 401: authentication credential..:(..Do you know how to fix that error.

    • blundell
      Posted June 2, 2012 at 9:49 am | Permalink | Reply

      You need to ensure the clock on your Emulator/Phone is set to the correct time, to allow Twitter oAuth to work

    • Posted June 2, 2012 at 12:47 pm | Permalink | Reply

      Correct time is what?I run in my phone
      and my device set time as time in my computer.I tried with your tutorial but it alway display 401..I also think cause is not correct time but I don’t know synchronize with twitter time.Do you help me.

    • kishor
      Posted May 6, 2013 at 9:18 am | Permalink | Reply

      I have same problem

      • blundell
        Posted May 10, 2013 at 9:29 pm | Permalink | Reply

        ensure your phone clock is correct and in the correct timezone

  38. nexicus
    Posted May 21, 2012 at 3:21 pm | Permalink | Reply

    Thanks for the the code it really helped me a lot. One question, how to share url link besided message and image in one tweet?

    • blundell
      Posted May 21, 2012 at 10:56 pm | Permalink | Reply

      Looking at the API I can’t see a way to attach pictures. I assume you just attach the URL (like in the tutorial) and twitter will parse it for an image if it has one.

  39. Victor
    Posted May 9, 2012 at 3:00 pm | Permalink | Reply

    I have imported your project in eclipse, added the necessary consumer key info and ran the app, but I get an error on the callback. it says that the website is not found for the callback url? I haven’t changed anything else…

    • blundell
      Posted May 9, 2012 at 4:33 pm | Permalink | Reply

      You may have missed something, have you added your consumer secret as well, and the callback URL in your manifest matches your class?

  40. Anthony
    Posted May 4, 2012 at 1:35 am | Permalink | Reply

    i tried running but cant continue to tweet since i cant login into twitter(the part where it needs my authentication). am i the only one here who got this kind of error? please help!

    • blundell
      Posted May 4, 2012 at 7:04 am | Permalink | Reply

      Yes Anthony you are :-) When people successfully tweet, it tweets at me an I get them all the time! Have you got your intents correctly declared in your manifest?

  41. Blade
    Posted April 27, 2012 at 10:33 am | Permalink | Reply

    Blundell,
    Thank you for such a nice piece of work. Most of the content I have found online is over complicated without a proper justification.
    Keep up the tutorials.
    Regards.

  42. Chris
    Posted April 11, 2012 at 3:23 pm | Permalink | Reply

    Thanks for the tutorial. However in my code in the dealWithTwitterResponse method the uri from the line uri = this.getIntent().getData() turns up null. Any idea why?

    • blundell
      Posted April 20, 2012 at 8:10 am | Permalink | Reply

      Hmm the intent shouldn’t be null really!

  43. Martin
    Posted April 10, 2012 at 4:18 pm | Permalink | Reply

    I think dealWithTwitterResponse should also handle case where users don’t go forward with login (cancel and return return to app). In this case, the uri returned wont have parameter “oauth_verifier” and the app will crash.

  44. Scott
    Posted March 26, 2012 at 4:48 am | Permalink | Reply

    In the authorizeNewUser method at mTwitter.getOAuthAccessToken(mReqToken, oauthVerifier) the app is returning an exception.

    mReqToken seems to be null.

    Any thoughts on this?

    • Scott
      Posted March 26, 2012 at 5:15 am | Permalink | Reply

      Nevermind, I had ‘Don’t keep activities’ active.

  45. Mert
    Posted March 16, 2012 at 5:21 pm | Permalink | Reply

    Hello thanks for example. I downloaded your project and tried to run that. I changed only consumer key and secret. but it doesn not work. When i press login, toast appears and says “Twitter Login error, try again later” . What did I do wrong?

    • blundell
      Posted March 17, 2012 at 9:07 am | Permalink | Reply

      Hi Mert,
      You’ll have to debug it, does the LogCat throw any exceptions? Did you have internet connection? Did you sign up to twitter correctly? Perhaps post a question on stackoverflow it has a nice Q&A design

      • Mert
        Posted March 19, 2012 at 10:02 am | Permalink | Reply

        03-19 10:01:47.806: I/Blundell.TweetToTwitterActivity(197): Login Pressed
        03-19 10:01:47.806: I/Blundell.TweetToTwitterActivity(197): New User
        03-19 10:01:47.806: I/Blundell.TweetToTwitterActivity(197): Request App Authentication
        03-19 10:01:48.744: D/dalvikvm(197): GC freed 6812 objects / 395744 bytes in 69ms
        03-19 10:01:48.844: I/global(197): Default buffer size used in BufferedReader constructor. It would be better to be explicit if an 8k-char buffer is required.
        03-19 10:01:48.844: I/NotificationService(52): enqueueToast pkg=com.blundell.tut.ttt callback=android.app.ITransientNotification$Stub$Proxy@44dbca90 duration=0

        when i press login , see theese on logcat

        • blundell
          Posted March 29, 2012 at 7:12 am | Permalink | Reply

          There is no error in that Log, is it still not working?

          • Tikam
            Posted July 31, 2012 at 5:02 pm | Permalink

            Dear Blundell,

            I am getting same, still not working, Please give a way to find out error.

          • blundell
            Posted August 1, 2012 at 7:23 am | Permalink

            I’ve just saw you get it working and tweet at me on Twitter! :-) Congratz!

          • Jason
            Posted September 1, 2012 at 5:43 am | Permalink

            Hi blundell, I am getting the same error as described above.
            I used your code, added my consumer key and consumer secret. My callback URL is “” (on the twitter app site and in the code) (not sure if this is an issue).

            log cat indicates:
            08-31 22:41:06.900: Arrived at onResume
            08-31 22:41:11.235: Login Pressed
            08-31 22:41:11.240: New User
            08-31 22:41:11.240: Request App Authentication

            I’m quite new to this and am stumped.

          • blundell
            Posted September 13, 2012 at 7:24 am | Permalink

            Yes it would probably be better if use used a callback URL that wasn’t blank!

  46. Posted March 8, 2012 at 1:36 pm | Permalink | Reply

    Hi blundell, does this code work for you when connected to a 3G/data connection? This and any other twitter4j examples I’ve tried only work on wifi for some reason :/

    • blundell
      Posted March 8, 2012 at 7:01 pm | Permalink | Reply

      Yes it should do I can’t see why not. It must be a device issue, or maybe when you create your APK it’s getting pro-guarded and that is removing the twitter4j jar? (random guess).

  47. Weeber
    Posted March 4, 2012 at 12:37 am | Permalink | Reply

    “Twitter Login error, try again later”

    The login is failing, I’m running the same code you posted, I just changed the CONSUMER_KEY and CONSUMER_SECRET to use my keys. The webview never shows up.

    • blundell
      Posted March 4, 2012 at 10:46 pm | Permalink | Reply

      You may have missed some code, as it works for many others. Have you checked your manifest? What else does the LogCat say?

  48. Kumar
    Posted February 21, 2012 at 4:58 pm | Permalink | Reply

    I would like to thank you for the sample code . It was really helpful. I created some addition methods to pass the mTwitter across the application but I am getting error in the setTwitter method. I have no idea why it is giving error. Please sujjest . I have pasted the code here http://pastebin.com/PKJcaSpJ

    • blundell
      Posted February 22, 2012 at 8:11 am | Permalink | Reply

      What is the error your getting? If you could post your question on http://stackoverflow.com and link it here I can help with an answer.

One Trackback

  1. By my onNewIntent is not calling | BlogoSfera on August 13, 2013 at 2:02 pm

Post a Comment

Your email is never shared. Required fields are marked *

*
*