2013-09-26 207 views
1

我還是Android編程的新手。我正在學習一本名爲Learning Android的書中的教程。當我點擊更新按鈕時,我最終崩潰。任何想法爲什麼? Stacktrace在下面。 我得到一個致命異常:主要Asynctask致命異常

package com.marakana.yamba; 

import winterwell.jtwitter.Twitter; 
import winterwell.jtwitter.TwitterException; 
import android.app.Activity; 
import android.os.AsyncTask; 
import android.os.Bundle; 
import android.util.Log; 
import android.view.Menu; 
import android.view.View; 
import android.view.View.OnClickListener; 
import android.widget.Button; 
import android.widget.EditText; 
import android.widget.Toast; 

public class StatusActivity extends Activity implements OnClickListener{ 

private static final String TAG ="StatusActivity"; 
    Twitter twitter; 
    EditText editText; 
    Button updateButton ; 
    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.status); 
//  Find Views 
     editText = (EditText) findViewById(R.id.editText); 
     updateButton = (Button) findViewById(R.id.updateButton); 
     updateButton.setOnClickListener(this); 

     twitter = new Twitter("Yamba18", "undertaker"); 

     twitter.setAPIRootUrl("http://yamba.marakana.com/api"); 


    } 


//Asynchronously Post to Twitter 
class PostToTwitter extends AsyncTask<String, Integer, String>{ 

    @Override 
    protected String doInBackground(String... statuses){ 
     try{ 
      winterwell.jtwitter.Status status = twitter.updateStatus(statuses[0]); 
      return status.text; 
     }catch(TwitterException e){ 
      Log.e(TAG,e.toString()); 
      e.printStackTrace(); 
      return "Failedd to Post"; 
     } 
    } 

    @Override 
    protected void onProgressUpdate (Integer... values){ 
     super.onProgressUpdate(values); 
    } 
    @Override 
    protected void onPostExecute(String result){ 
     Toast.makeText(StatusActivity.this, result, Toast.LENGTH_LONG).show(); 
    } 
} 



public void onClick(View v){ 

    twitter.setStatus(editText.getText().toString()); 
    Log.d(TAG, "onClicked"); 
} 
@Override 
public boolean onCreateOptionsMenu(Menu menu) { 
    // Inflate the menu; this adds items to the action bar if it is present. 
    getMenuInflater().inflate(R.menu.status, menu); 
    return true; 
} 
} 

這裏的logcat的。

09-26 17:25:56.469: D/AndroidRuntime(612): Shutting down VM 
09-26 17:25:56.469: W/dalvikvm(612): threadid=1: thread exiting with uncaught exception (group=0x409961f8) 
09-26 17:25:56.529: E/AndroidRuntime(612): FATAL EXCEPTION: main 
09-26 17:25:56.529: E/AndroidRuntime(612): winterwell.jtwitter.TwitterException: java.io.IOException: Received authentication challenge is null 
09-26 17:25:56.529: E/AndroidRuntime(612): at winterwell.jtwitter.URLConnectionHttpClient.processError(URLConnectionHttpClient.java:533) 
09-26 17:25:56.529: E/AndroidRuntime(612): at winterwell.jtwitter.URLConnectionHttpClient.post2_connect(URLConnectionHttpClient.java:413) 
09-26 17:25:56.529: E/AndroidRuntime(612): at winterwell.jtwitter.URLConnectionHttpClient.post2(URLConnectionHttpClient.java:379) 
09-26 17:25:56.529: E/AndroidRuntime(612): at winterwell.jtwitter.URLConnectionHttpClient.post(URLConnectionHttpClient.java:348) 
09-26 17:25:56.529: E/AndroidRuntime(612): at winterwell.jtwitter.Twitter.updateStatus(Twitter.java:2762) 
09-26 17:25:56.529: E/AndroidRuntime(612): at winterwell.jtwitter.Twitter.updateStatus(Twitter.java:2694) 
09-26 17:25:56.529: E/AndroidRuntime(612): at winterwell.jtwitter.Twitter.setStatus(Twitter.java:2482) 
09-26 17:25:56.529: E/AndroidRuntime(612): at com.marakana.yamba.StatusActivity.onClick(StatusActivity.java:68) 
09-26 17:25:56.529: E/AndroidRuntime(612): at android.view.View.performClick(View.java:3480) 
09-26 17:25:56.529: E/AndroidRuntime(612): at android.view.View$PerformClick.run(View.java:13983) 
09-26 17:25:56.529: E/AndroidRuntime(612): at android.os.Handler.handleCallback(Handler.java:605) 
09-26 17:25:56.529: E/AndroidRuntime(612): at android.os.Handler.dispatchMessage(Handler.java:92) 
09-26 17:25:56.529: E/AndroidRuntime(612): at android.os.Looper.loop(Looper.java:137) 
09-26 17:25:56.529: E/AndroidRuntime(612): at android.app.ActivityThread.main(ActivityThread.java:4340) 
09-26 17:25:56.529: E/AndroidRuntime(612): at java.lang.reflect.Method.invokeNative(Native Method) 
09-26 17:25:56.529: E/AndroidRuntime(612): at java.lang.reflect.Method.invoke(Method.java:511) 
09-26 17:25:56.529: E/AndroidRuntime(612): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:784) 
09-26 17:25:56.529: E/AndroidRuntime(612): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:551) 
09-26 17:25:56.529: E/AndroidRuntime(612): at dalvik.system.NativeStart.main(Native Method) 
09-26 17:25:56.529: E/AndroidRuntime(612): Caused by: java.io.IOException: Received authentication challenge is null 
09-26 17:25:56.529: E/AndroidRuntime(612): at libcore.net.http.HttpURLConnectionImpl.processAuthHeader(HttpURLConnectionImpl.java:397) 
09-26 17:25:56.529: E/AndroidRuntime(612): at libcore.net.http.HttpURLConnectionImpl.processResponseHeaders(HttpURLConnectionImpl.java:345) 
09-26 17:25:56.529: E/AndroidRuntime(612): at libcore.net.http.HttpURLConnectionImpl.getResponse(HttpURLConnectionImpl.java:276) 
09-26 17:25:56.529: E/AndroidRuntime(612): at libcore.net.http.HttpURLConnectionImpl.getResponseCode(HttpURLConnectionImpl.java:479) 
09-26 17:25:56.529: E/AndroidRuntime(612): at winterwell.jtwitter.URLConnectionHttpClient.processError(URLConnectionHttpClient.java:468) 
09-26 17:25:56.529: E/AndroidRuntime(612): ... 18 more 
09-26 17:25:59.169: I/Process(612): Sending signal. PID: 612 SIG: 9 

回答

2

類似的例子爲我工作,希望它有助於有點:

  • 添加庫:路標(signpost-core-1.2.1.1.jar)
  • 在Web上生成OAUTH_KEY和OAUTH_SECRET:https://dev.twitter.com/apps/
  • 修改MainActivity.java:

    private static final String OAUTH_KEY = "your_OAUTH_KEY"; 
    private static final String OAUTH_SECRET = "your_OAUTH_SECRET"; 
    private static final String TWITTER_USER = "your_email"; 
    

我的文件:

MainActivity.java

package com.marakana.oauth; 

import com.marakana.oauth.R;  
import oauth.signpost.OAuth; 
import oauth.signpost.OAuthConsumer; 
import oauth.signpost.OAuthProvider; 
import oauth.signpost.basic.DefaultOAuthConsumer; 
import oauth.signpost.basic.DefaultOAuthProvider; 
import oauth.signpost.exception.OAuthCommunicationException; 
import oauth.signpost.exception.OAuthExpectationFailedException; 
import oauth.signpost.exception.OAuthMessageSignerException; 
import oauth.signpost.exception.OAuthNotAuthorizedException; 
import winterwell.jtwitter.OAuthSignpostClient; 
import winterwell.jtwitter.Twitter; 
import winterwell.jtwitter.TwitterException; 
import android.app.Activity; 
import android.content.Intent; 
import android.content.SharedPreferences; 
import android.net.Uri; 
import android.os.AsyncTask; 
import android.os.Bundle; 
import android.preference.PreferenceManager; 
import android.util.Log; 
import android.view.View; 
import android.widget.EditText; 
import android.widget.Toast; 

public class MainActivity extends Activity { 

    private static final String TAG = "OAuthDemo"; 

    /******************************** 
     Generate your values ​​on the web:: 
     https://dev.twitter.com/apps/ 
    *********************************/ 
    private static final String OAUTH_KEY = "your_OAUTH_KEY"; 
    private static final String OAUTH_SECRET = "your_OAUTH_SECRET"; 
    private static final String TWITTER_USER = "your_email"; 

    private static final String OAUTH_CALLBACK_SCHEME = "x-marakana-oauth-twitter"; 
    private static final String OAUTH_CALLBACK_URL = OAUTH_CALLBACK_SCHEME + "://callback"; 
    private OAuthSignpostClient oauthClient; 
    private OAuthConsumer mConsumer; 
    private OAuthProvider mProvider; 
    private Twitter twitter; 
    SharedPreferences prefs; 

    /** Called when the activity is first created. */ 
    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.activity_main); 
     mConsumer = new DefaultOAuthConsumer(OAUTH_KEY, OAUTH_SECRET); 
     //mConsumer = new CommonsHttpOAuthConsumer(OAUTH_KEY, OAUTH_SECRET); 
     mProvider = new DefaultOAuthProvider(
       "https://api.twitter.com/oauth/request_token", 
       "https://api.twitter.com/oauth/access_token", 
       "https://api.twitter.com/oauth/authorize"); 

     // Read the prefs to see if we have token 
     prefs = PreferenceManager.getDefaultSharedPreferences(this); 
     String token = prefs.getString("token", null); 
     String tokenSecret = prefs.getString("tokenSecret", null); 
     if (token != null && tokenSecret != null) { 
      // We have token, use it 
      mConsumer.setTokenWithSecret(token, tokenSecret); 
      // Make a Twitter object 
      oauthClient = new OAuthSignpostClient(OAUTH_KEY, OAUTH_SECRET, 
        token, tokenSecret); 
      twitter = new Twitter(TWITTER_USER, oauthClient); 
     } 
    } 

    /* 
    * Callback once we are done with the authorization of this app with 
    * Twitter. 
    */ 
    @Override 
    public void onNewIntent(Intent intent) { 
     super.onNewIntent(intent); 
     Log.d(TAG, "intent: " + intent); 

     // Check if this is a callback from OAuth 
     Uri uri = intent.getData(); 
     if (uri != null && uri.getScheme().equals(OAUTH_CALLBACK_SCHEME)) { 
      Log.d(TAG, "callback: " + uri.getPath()); 

      String verifier = uri.getQueryParameter(OAuth.OAUTH_VERIFIER); 
      Log.d(TAG, "verifier: " + verifier); 

      new RetrieveAccessTokenTask().execute(verifier); 
     } 

    } 

    public void onClickAuthorize(View view) { 
     new OAuthAuthorizeTask().execute(); 
    } 

    public void onClickTweet(View view) { 
     if (twitter == null) { 
      Toast.makeText(this, "Authenticate first", Toast.LENGTH_LONG) 
        .show(); 
      return; 
     } 

     EditText status = (EditText) findViewById(R.id.status); 
     new PostStatusTask().execute(status.getText().toString()); 
    } 

    public void onClickGetStatus(View view) { 
     if (twitter == null) { 
      Toast.makeText(this, "Authenticate first", Toast.LENGTH_LONG) 
        .show(); 
      return; 
     } 
     new GetStatusTask().execute(); 
    } 

    /* Responsible for starting the Twitter authorization */ 
    class OAuthAuthorizeTask extends AsyncTask<Void, Void, String> { 

     @Override 
     protected String doInBackground(Void... params) { 
      String authUrl; 
      String message = null; 
      try { 
       authUrl = mProvider.retrieveRequestToken(mConsumer, 
         OAUTH_CALLBACK_URL); 
       Intent intent = new Intent(Intent.ACTION_VIEW, 
         Uri.parse(authUrl)); 
       startActivity(intent); 
      } catch (OAuthMessageSignerException e) { 
       message = "OAuthMessageSignerException"; 
       e.printStackTrace(); 
      } catch (OAuthNotAuthorizedException e) { 
       message = "OAuthNotAuthorizedException"; 
       e.printStackTrace(); 
      } catch (OAuthExpectationFailedException e) { 
       message = "OAuthExpectationFailedException"; 
       e.printStackTrace(); 
      } catch (OAuthCommunicationException e) { 
       message = "OAuthCommunicationException"; 
       e.printStackTrace(); 
      } 
      return message; 
     } 

     @Override 
     protected void onPostExecute(String result) { 
      super.onPostExecute(result); 
      if (result != null) { 
       Toast.makeText(MainActivity.this, result, Toast.LENGTH_LONG) 
         .show(); 
      } 
     } 
    } 

    /* Responsible for retrieving access tokens from twitter */ 
    class RetrieveAccessTokenTask extends AsyncTask<String, Void, String> { 

     @Override 
     protected String doInBackground(String... params) { 
      String message = null; 
      String verifier = params[0]; 
      try { 
       // Get the token 
       Log.d(TAG, "mConsumer: " + mConsumer); 
       Log.d(TAG, "mProvider: " + mProvider); 
       mProvider.retrieveAccessToken(mConsumer, verifier); 
       String token = mConsumer.getToken(); 
       String tokenSecret = mConsumer.getTokenSecret(); 
       mConsumer.setTokenWithSecret(token, tokenSecret); 

       Log.d(TAG, String.format(
         "verifier: %s, token: %s, tokenSecret: %s", verifier, 
         token, tokenSecret)); 

       // Store token in prefs 
       prefs.edit().putString("token", token) 
         .putString("tokenSecret", tokenSecret).commit(); 

       // Make a Twitter object 
       oauthClient = new OAuthSignpostClient(OAUTH_KEY, OAUTH_SECRET, 
         token, tokenSecret); 

       /* "NameTest" (any word) */ 
       twitter = new Twitter("NameTest", oauthClient); 

       Log.d(TAG, "token: " + token); 
      } catch (OAuthMessageSignerException e) { 
       message = "OAuthMessageSignerException"; 
       e.printStackTrace(); 
      } catch (OAuthNotAuthorizedException e) { 
       message = "OAuthNotAuthorizedException"; 
       e.printStackTrace(); 
      } catch (OAuthExpectationFailedException e) { 
       message = "OAuthExpectationFailedException"; 
       e.printStackTrace(); 
      } catch (OAuthCommunicationException e) { 
       message = "OAuthCommunicationException"; 
       e.printStackTrace(); 
      } 
      return message; 
     } 

     @Override 
     protected void onPostExecute(String result) { 
      super.onPostExecute(result); 
      if (result != null) { 
       Toast.makeText(MainActivity.this, result, Toast.LENGTH_LONG) 
         .show(); 
      } 
     } 
    } 

    /* Responsible for getting Twitter status */ 
    class GetStatusTask extends AsyncTask<Void, Void, String> { 
     @Override 
     protected String doInBackground(Void... params) { 
      return twitter.getStatus().text; 
     } 

     @Override 
     protected void onPostExecute(String result) { 
      super.onPostExecute(result); 
      Toast.makeText(MainActivity.this, result, Toast.LENGTH_LONG).show(); 
     } 
    } 

    /* Responsible for posting new status to Twitter */ 
    class PostStatusTask extends AsyncTask<String, Void, String> { 
     @Override 
     protected String doInBackground(String... params) { 
      try { 
       twitter.setStatus(params[0]); 
       return "Successfully posted: " + params[0]; 
      } catch (TwitterException e) { 
       return "Error connecting to server."; 
      } 
     } 

     @Override 
     protected void onPostExecute(String result) { 
      super.onPostExecute(result); 
      Toast.makeText(MainActivity.this, result, Toast.LENGTH_LONG).show(); 
     } 

    } 
} 

AndroidManifest.xml中

<?xml version="1.0" encoding="utf-8"?> 
<manifest 
    xmlns:android="http://schemas.android.com/apk/res/android" 
    package="com.marakana.oauth" 
    android:versionCode="1" 
    android:versionName="1.0"> 
    <uses-sdk 
    android:minSdkVersion="11" /> 
    <uses-permission 
    android:name="android.permission.INTERNET" /> 

    <application 
    android:icon="@drawable/ic_launcher" 
    android:label="@string/app_name"> 
    <activity 
     android:name=".MainActivity" 
     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> 

     <!-- Used for OAuth callback --> 
     <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="x-marakana-oauth-twitter" 
      android:host="callback" /> 
     </intent-filter> 

    </activity> 

    </application> 
</manifest> 

activity_main.xml中

<?xml version="1.0" encoding="utf-8"?> 
<LinearLayout 
    xmlns:android="http://schemas.android.com/apk/res/android" 
    android:orientation="vertical" 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" 
    android:gravity="center_horizontal"> 

    <TextView 
    android:layout_width="match_parent" 
    android:layout_height="wrap_content" 
    android:text="@string/app_name" 
    android:textSize="50sp" 
    android:gravity="center" /> 
    <Button 
    android:layout_width="wrap_content" 
    android:layout_height="wrap_content" 
    android:text="Authenticate" 
    android:onClick="onClickAuthorize" 
    android:textSize="40sp"></Button> 
    <EditText 
    android:layout_height="wrap_content" 
    android:layout_width="match_parent" 
    android:id="@+id/status" 
    android:textSize="40sp" 
    android:hint="What's up?"></EditText> 
    <Button 
    android:layout_width="wrap_content" 
    android:layout_height="wrap_content" 
    android:text="Tweet" 
    android:onClick="onClickTweet" 
    android:textSize="40sp"></Button> 
    <Button 
    android:layout_width="wrap_content" 
    android:layout_height="wrap_content" 
    android:text="Get Status" 
    android:textSize="40sp" 
    android:onClick="onClickGetStatus"></Button> 

</LinearLayout>