2013-10-16 1 views
2

나는 여기를 잃고있다. RESTful API에서 가져온 데이터를 사용하여 내 Activity에서 List를 채우려고합니다. Apache HttpClient 라이브러리 (org.apache.http.client)를 사용하여 API와 (성공적으로) 대화하는 API 레이어를 만들었습니다. 그러나 AsyncTask를 통해 Activity를 API 레이어에 연결하려고 시도했을 때 재앙이 발생했습니다. 문제의 코드에서 API 레이어를 제거하고 대신 문제를 (문제가없는) 분리하려고 생각할 수있는 가장 간단한 예제를 삽입했습니다. 나는 안드로이드 프로그래밍 비교적 새로운 해요 (그리고 한 동안 자바 손도 안) 그래서 어떤 도움안드로이드와 AsyncTask에서 HttpClient를 사용하는 FatalException

10-16 19:36:04.264: ERROR/AndroidRuntime(633): FATAL EXCEPTION: AsyncTask #1 
    java.lang.RuntimeException: An error occured while executing doInBackground() 
    at android.os.AsyncTask$3.done(AsyncTask.java:200) 
    at java.util.concurrent.FutureTask$Sync.innerSetException(FutureTask.java:274) 
    at java.util.concurrent.FutureTask.setException(FutureTask.java:125) 
    at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:308) 
    at java.util.concurrent.FutureTask.run(FutureTask.java:138) 
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1088) 
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:581) 
    at java.lang.Thread.run(Thread.java:1019) 
    Caused by: java.lang.ExceptionInInitializerError 
    at org.apache.http.impl.conn.PoolingHttpClientConnectionManager$InternalConnectionFactory.<init>(PoolingHttpClientConnectionManager.java:487) 
    at org.apache.http.impl.conn.PoolingHttpClientConnectionManager.<init>(PoolingHttpClientConnectionManager.java:147) 
    at org.apache.http.impl.conn.PoolingHttpClientConnectionManager.<init>(PoolingHttpClientConnectionManager.java:136) 
    at org.apache.http.impl.conn.PoolingHttpClientConnectionManager.<init>(PoolingHttpClientConnectionManager.java:112) 
    at org.apache.http.impl.client.HttpClientBuilder.build(HttpClientBuilder.java:727) 
    at org.apache.http.impl.client.HttpClients.createDefault(HttpClients.java:58) 
    at ca.redacted.app.MyActivity$GetEventsTask.fetch(MyActivity.java:70) 
    at ca.redacted.app.MyActivity$GetEventsTask.doInBackground(MyActivity.java:49) 
    at ca.redacted.app.MyActivity$GetEventsTask.doInBackground(MyActivity.java:44) 
    at android.os.AsyncTask$2.call(AsyncTask.java:185) 
    at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:306) 
    ... 4 more 
    Caused by: java.lang.ExceptionInInitializerError 
    at org.apache.http.impl.conn.ManagedHttpClientConnectionFactory.<init>(ManagedHttpClientConnectionFactory.java:72) 
    at org.apache.http.impl.conn.ManagedHttpClientConnectionFactory.<init>(ManagedHttpClientConnectionFactory.java:84) 
    at org.apache.http.impl.conn.ManagedHttpClientConnectionFactory.<clinit>(ManagedHttpClientConnectionFactory.java:59) 
    ... 15 more 
    Caused by: java.lang.NoSuchFieldError: org.apache.http.message.BasicLineFormatter.INSTANCE 
    at org.apache.http.impl.io.DefaultHttpRequestWriterFactory.<init>(DefaultHttpRequestWriterFactory.java:52) 
    at org.apache.http.impl.io.DefaultHttpRequestWriterFactory.<init>(DefaultHttpRequestWriterFactory.java:56) 
    at org.apache.http.impl.io.DefaultHttpRequestWriterFactory.<clinit>(DefaultHttpRequestWriterFactory.java:46) 
    ... 18 more 

: 여기

public class MyActivity extends Activity { 

@Override 
protected void onCreate(Bundle savedInstanceState) { 

    super.onCreate(savedInstanceState); 
    setContentView(R.layout.main); 
} 

@Override 
protected void onResume() { 

    super.onResume(); 
    new GetEventsTask().execute(); 
} 

private class GetEventsTask extends AsyncTask<Object, Integer, List<IEvent>> { 

    @Override 
    protected List<IEvent> doInBackground(Object... params) { 

     fetch(); 
     return null; 
    } 

    @Override 
    protected void onPostExecute(List<IEvent> events) { 

     Toast.makeText(getApplicationContext(), "Success", Toast.LENGTH_SHORT).show(); 
    } 

    private void fetch() { 
     CloseableHttpClient client = HttpClients.createDefault(); 
     HttpPost httpPost = new HttpPost("https://someurl.com/login"); 

     List<NameValuePair> data = new ArrayList<NameValuePair>(); 
     data.add(new BasicNameValuePair("username", "hai")); 
     data.add(new BasicNameValuePair("password", "kthxbye")); 

     try { 
      httpPost.setEntity(new UrlEncodedFormEntity(data)); 
      CloseableHttpResponse response = client.execute(httpPost); 
     } catch(Exception e) { 
      Toast.makeText(getApplicationContext(), "Caught Exception", Toast.LENGTH_SHORT).show(); 
     } 
    } 
} 

그리고 스택 추적한다 : 여기에 문제의 코드는 대단히 감사합니다.

업데이트 디버그 실행을 기반으로 ,이

CloseableHttpClient 클라이언트 = HttpClients.createDefault()을 FatalException을 던지고 라인입니다;

은 다시 안드로이드 DefaultHttpClient 구현 (경우 다른 사람이 아파치 버전을 사용하는 문제로 실행에) 문제를 해결 공급 사용 전환

업데이트되었습니다. 아직도 다른 도서관에서 저를 슬프게하는 원인이 무엇인지 모르겠습니다.

+2

온라인 70은 무엇입니까? – Emmanuel

+0

CloseableHttpClient 클라이언트 = HttpClients.createDefault(); – BeardedCoder

답변

2

HttpClients가 Android 코드에서 빌드되지 않기 때문에 아파치 라이브러리를 추가했다고 가정합니다. here을 참조하십시오. 런타임이 발생하는 이유는 예외이지만 컴파일 예외는 아닙니다. 라이브러리가 내보내기되지 않았기 때문에 해당 예외가 있다고 가정합니다. 귀하의 신청서와 함께. 에,

는이 문제를 해결하기 위해
CloseableHttpClient client = HttpClients.createDefault(); 

, 당신은 응용 프로그램과 외부 아파치 라이브러리를 내 보내야합니다 :

ExceptionInInitializerError 

은 (HttpClients) 여기를 가리키는 정적 클래스를로드하지 못했습니다 것을 의미한다 일식 :

Project-> config 빌드 경로 -> 내보낼 라이브러리를 선택하십시오.

덧붙여서, @codeMagic은 UI 스레드에서 실행해야하기 때문에 catch 절이 Toast를 사용할 수 없다고 지적했습니다. 현재 코드가 try 절에 도달하지 못하기 때문에 예외가 발생하지는 않지만 머리를 위로 올려야합니다.

+0

IntelliJ를 사용하고 있지만 프로젝트 구조> 모듈> 종속성으로 이동하여 필수 라이브러리의 내보내기를 선택했습니다. 그러나 변화는 없습니다. – BeardedCoder

+1

사용중인 클래스를 사용해야하는 경우를 제외하고는 DefaultHttpClient와 같은 다른 클라이언트를 사용하는 것이 좋습니다. 구글이 안드로이드 패키지에'HttpClients'를 포함시키지 않기로 결정한 이유가있을 수 있습니다. [참조] (http://android-developers.blogspot.com/2011/09/androids-http-clients.html) – wtsang02

+0

그래서 DefaultHttpClient로 전환하면 문제가 해결되었습니다. 감사! 아직도 다른 하나가 작동하지 않았다는 것을 아직도 모릅니다. – BeardedCoder

1

내가보기에 이것은 현재 문제인 것처럼 보이지 않지만 어느 시점에서는 문제가 될 것입니다. 이 라인은

catch(Exception e) { 
     Toast.makeText(getApplicationContext(), "Caught Exception", Toast.LENGTH_SHORT).show(); 

UI을 업데이트하고이 doInBackground()에서 호출되기 때문에이 예외가 발생하는 배경 Thread에서 실행되고 있습니다. 이를 처리하는 방법은 responseonPostExecute()으로 전달하고 응답 유형에 따라 UI을 거기에서 업데이트하는 것입니다.

According to the Java Documentation

이 예외는 static Class을 초기화 문제에서 비롯됩니다. 이 줄에서 뒤로 추적하십시오.

CloseableHttpClient client = HttpClients.createDefault(); 

왜 실패하는지보십시오.

+1

또한 doinBackground의 catch()에서 Log.e (태그, 메시지, 예외)를 사용하여 자세한 정보를 얻으십시오 .. –

+0

고마워요. 나는 그 일을 어떤 일이 벌어지고 있는지 알아 내려고 분노한 채 저주했다. – BeardedCoder

+0

@Merrdin as K5 사용자가 댓글을 달았습니다. 로그를 사용합니다. – codeMagic

관련 문제