AsyncTask中的NetworkOnMainThreadException

时间:2014-07-10 08:36:35

标签: android android-asynctask networkonmainthread

我在NetworkOnMainThreadException执行两个网络请求时收到AsyncTask。在第一个请求中,我获得了Response XML,在第二个请求中,我下载了Image InputStream中要使用的BitmapFactory.decodeStream。请在下面找到例外:

NetworkOnMainThreadException

07-10 08:20:49.961: W/System.err(8570): android.os.NetworkOnMainThreadException
07-10 08:20:49.961: W/System.err(8570):     at android.os.StrictMode$AndroidBlockGuardPolicy.onNetwork(StrictMode.java:1117)
07-10 08:20:49.961: W/System.err(8570):     at libcore.io.BlockGuardOs.recvfrom(BlockGuardOs.java:163)
07-10 08:20:49.971: W/System.err(8570):     at libcore.io.IoBridge.recvfrom(IoBridge.java:513)
07-10 08:20:49.971: W/System.err(8570):     at java.net.PlainSocketImpl.read(PlainSocketImpl.java:488)
07-10 08:20:49.971: W/System.err(8570):     at java.net.PlainSocketImpl.access$000(PlainSocketImpl.java:46)
07-10 08:20:49.971: W/System.err(8570):     at java.net.PlainSocketImpl$PlainSocketInputStream.read(PlainSocketImpl.java:240)
07-10 08:20:49.981: W/System.err(8570):     at java.io.BufferedInputStream.read(BufferedInputStream.java:304)

AyncTask

public class FetchDataTask extends AsyncTask {

    @Override
    protected Object doInBackground(Object... object) {
        String url = (String)object[0];
        TASK_TYPE type = (TASK_TYPE)object[1];
        Object[] objects = new Object[4];
        switch(type)
        {
        case FETCH_NOTICES:
            publishProgress("Fetching notices ...");

             // Request # 1 to get the JSON XML

            String data = apiRequestGET(url);
            ArrayList<Notices> notices = extractUserFriendsDataFromXML(data);
            Notices notice = notices.get(0);

            publishProgress("Fetching done.");
            objects[0] = type;
            objects[1] = new ArrayList<Notices>(notices.subList(1, notices.size()));
            objects[2] = notice.getUniversityTitle();
            try {

             // Request # 2 to get the InputStream

                objects[3] = (InputStream) new URL(notice.getUniversityLogo()).getContent();
            } catch (MalformedURLException e1) {
                // TODO Auto-generated catch block
                e1.printStackTrace();
            } catch (IOException e1) {
                // TODO Auto-generated catch block
                e1.printStackTrace();
            }
            return objects; 
        }

        return null;
    }

    private String apiRequestGET(String requestString)
    {
        HttpClient httpClient = new DefaultHttpClient();
        HttpContext localContext = new BasicHttpContext();
        HttpGet httpGet = new HttpGet(requestString);

        String responseText = null;
        try 
        {
            HttpResponse response = httpClient.execute(httpGet, localContext);
            System.out.println("Some Response" +response);
            HttpEntity entity = response.getEntity();
            responseText = EntityUtils.toString(entity);
        }
        catch (Exception e1) 
        {
            return e1.getLocalizedMessage();
        }
        return responseText;
    }

}

有谁能告诉我我做错了什么? doInBackground中的两个网络请求无法完成?

提前致谢!

编辑完整堆栈跟踪

07-10 08:52:18.672: W/System.err(9213): android.os.NetworkOnMainThreadException
07-10 08:52:18.682: W/System.err(9213):     at android.os.StrictMode$AndroidBlockGuardPolicy.onNetwork(StrictMode.java:1117)
07-10 08:52:18.682: W/System.err(9213):     at libcore.io.BlockGuardOs.recvfrom(BlockGuardOs.java:163)
07-10 08:52:18.682: W/System.err(9213):     at libcore.io.IoBridge.recvfrom(IoBridge.java:513)
07-10 08:52:18.692: W/System.err(9213):     at java.net.PlainSocketImpl.read(PlainSocketImpl.java:488)
07-10 08:52:18.692: W/System.err(9213):     at java.net.PlainSocketImpl.access$000(PlainSocketImpl.java:46)
07-10 08:52:18.692: W/System.err(9213):     at java.net.PlainSocketImpl$PlainSocketInputStream.read(PlainSocketImpl.java:240)
07-10 08:52:18.702: W/System.err(9213):     at java.io.BufferedInputStream.read(BufferedInputStream.java:304)
07-10 08:52:18.702: W/System.err(9213):     at libcore.net.http.FixedLengthInputStream.read(FixedLengthInputStream.java:45)
07-10 08:52:18.702: W/System.err(9213):     at java.io.BufferedInputStream.fillbuf(BufferedInputStream.java:168)
07-10 08:52:18.702: W/System.err(9213):     at java.io.BufferedInputStream.read(BufferedInputStream.java:309)
07-10 08:52:18.712: W/System.err(9213):     at android.graphics.BitmapFactory.nativeDecodeStream(Native Method)
07-10 08:52:18.712: W/System.err(9213):     at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:529)
07-10 08:52:18.712: W/System.err(9213):     at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:601)
07-10 08:52:18.722: W/System.err(9213):     at com.alpha.noticeslist.NoticeListActivity.dataFetched(NoticeListActivity.java:145)
07-10 08:52:18.722: W/System.err(9213):     at com.alpha.web.FetchDataTask.onPostExecute(FetchDataTask.java:124)
07-10 08:52:18.732: W/System.err(9213):     at android.os.AsyncTask.finish(AsyncTask.java:631)
07-10 08:52:18.732: W/System.err(9213):     at android.os.AsyncTask.access$600(AsyncTask.java:177)
07-10 08:52:18.732: W/System.err(9213):     at android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.java:644)
07-10 08:52:18.732: W/System.err(9213):     at android.os.Handler.dispatchMessage(Handler.java:99)
07-10 08:52:18.742: W/System.err(9213):     at android.os.Looper.loop(Looper.java:137)
07-10 08:52:18.742: W/System.err(9213):     at android.app.ActivityThread.main(ActivityThread.java:5041)
07-10 08:52:18.752: W/System.err(9213):     at java.lang.reflect.Method.invokeNative(Native Method)
07-10 08:52:18.752: W/System.err(9213):     at java.lang.reflect.Method.invoke(Method.java:511)
07-10 08:52:18.752: W/System.err(9213):     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:793)
07-10 08:52:18.752: W/System.err(9213):     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:560)
07-10 08:52:18.762: W/System.err(9213):     at dalvik.system.NativeStart.main(Native Method)

我从onPostExecute调用InputStream传递的函数时得到错误:

public void dataFetched(InputStream inputstream)
    {       
            Bitmap bitmap = BitmapFactory.decodeStream(inputstream);
            logo.setImageBitmap(bitmap);
    }

onPostExecute

@Override
    protected void onPostExecute(Object result){
        statusDialog.dismiss();
        Object[] objects = (Object[])result;
        TASK_TYPE type = (TASK_TYPE)objects[0];
        switch(type)
        {
        case FETCH_NOTICES:
        ((NoticeListActivity)callerActivity).dataFetched((InputStream)objects[3]);
        break;
        }
    }

4 个答案:

答案 0 :(得分:1)

我认为您收到了错误,因为虽然您在后台主题中获得了对InputStream的引用,但实际上当您在decodeStream中调用onPostExecute时,您会从流中读取该内容在主线程上运行

移动电话:

Bitmap bitmap = BitmapFactory.decodeStream(inputstream);

进入doInBackground并传递bitmap而不是输入流

答案 1 :(得分:0)

确保您致电myFetchDataTask.execute()。您是否直接致电doInBackground(),如果是这样,它将无效,如果没有,请发布您执行AsyncTask的方式。

希望它有所帮助!

答案 2 :(得分:0)

你的班级应该是:

class FetchDataTask extends AsyncTask<Object, String, Void> 
    {

        @Override
        protected Void doInBackground(Object... params) {
            //code here

            publishProgress("");

            return null;
        }

        @Override
        protected void onProgressUpdate(String... values) {
            // TODO Auto-generated method stub
            super.onProgressUpdate(values);
        }
    }

您可以执行new FetchDataTask.execute([your parameter]);

答案 3 :(得分:-1)

使用以下代码执行异步任务:

private class FetchDataTask  extends AsyncTask <String, Void, Void>

{
Object[] objects = new Object[4];
protected void onPreExecute() {
}
@Override
protected Void doInBackground(String... paramsObj) {
    String url = (String)object[0];
    TASK_TYPE type = (TASK_TYPE)object[1];

    switch(type)
    {
    case FETCH_NOTICES:
        publishProgress("Fetching notices ...");

        // Request # 1 to get the JSON XML

        String data = apiRequestGET(url);
        ArrayList<Notices> notices = extractUserFriendsDataFromXML(data);
        Notices notice = notices.get(0);

        publishProgress("Fetching done.");
        objects[0] = type;
        objects[1] = new ArrayList<Notices>(notices.subList(1, notices.size()));
        objects[2] = notice.getUniversityTitle();
        try {

            // Request # 2 to get the InputStream

            objects[3] = (InputStream) new URL(notice.getUniversityLogo()).getContent();
        } catch (MalformedURLException e1) {
            // TODO Auto-generated catch block
            e1.printStackTrace();
        } catch (IOException e1) {
            // TODO Auto-generated catch block
            e1.printStackTrace();
        }
    }

    return null;
}

protected void onPostExecute(Void unused) 
{
    // Do action with objects
}

}

从调用方法中,使用:

new FetchDataTask().execute();