如何修复“android.os.NetworkOnMainThreadException”?

新手上路,请多包涵

为 RssReader 运行我的 Android 项目时出现错误。

代码:

 URL url = new URL(urlToRssFeed);
SAXParserFactory factory = SAXParserFactory.newInstance();
SAXParser parser = factory.newSAXParser();
XMLReader xmlreader = parser.getXMLReader();
RssHandler theRSSHandler = new RssHandler();
xmlreader.setContentHandler(theRSSHandler);
InputSource is = new InputSource(url.openStream());
xmlreader.parse(is);
return theRSSHandler.getFeed();

它显示以下错误:

 android.os.NetworkOnMainThreadException

我该如何解决这个问题?

原文由 bejoy george 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 663
2 个回答

注意:AsyncTask 在 API 级别 30 中被弃用。

异步任务 |安卓开发者

当应用程序试图在其主线程上执行网络操作时会抛出此异常。在 AsyncTask 中运行您的代码:

 class RetrieveFeedTask extends AsyncTask<String, Void, RSSFeed> {

    private Exception exception;

    protected RSSFeed doInBackground(String... urls) {
        try {
            URL url = new URL(urls[0]);
            SAXParserFactory factory = SAXParserFactory.newInstance();
            SAXParser parser = factory.newSAXParser();
            XMLReader xmlreader = parser.getXMLReader();
            RssHandler theRSSHandler = new RssHandler();
            xmlreader.setContentHandler(theRSSHandler);
            InputSource is = new InputSource(url.openStream());
            xmlreader.parse(is);

            return theRSSHandler.getFeed();
        } catch (Exception e) {
            this.exception = e;

            return null;
        } finally {
            is.close();
        }
    }

    protected void onPostExecute(RSSFeed feed) {
        // TODO: check this.exception
        // TODO: do something with the feed
    }
}

如何执行任务:

MainActivity.java 文件中,您可以在 oncreate() 方法中添加这一行

new RetrieveFeedTask().execute(urlToRssFeed);

不要忘记将此添加到 AndroidManifest.xml 文件:

 <uses-permission android:name="android.permission.INTERNET"/>

原文由 Michael Spector 发布,翻译遵循 CC BY-SA 4.0 许可协议

您几乎应该始终在线程上或作为异步任务运行网络操作。

但是,如果您愿意接受后果, 可以删除此限制并覆盖默认行为。

添加:

 StrictMode.ThreadPolicy policy = new StrictMode.ThreadPolicy.Builder().permitAll().build();

StrictMode.setThreadPolicy(policy);

在你的课堂上,

在 Android manifest.xml 文件中 添加 此权限:

 <uses-permission android:name="android.permission.INTERNET"/>

结果:

您的应用程序将(在不稳定的 Internet 连接区域)变得无响应并锁定,用户感知到缓慢并且必须强制终止,并且您冒着活动管理器终止您的应用程序并告诉用户该应用程序已停止的风险。

Android 有一些关于响应式设计的良好编程实践的好技巧: NetworkOnMainThreadException |安卓开发者

原文由 user1169115 发布,翻译遵循 CC BY-SA 4.0 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题