收到所有数据后关闭流

问题描述

我正在尝试发出一个 HTTP 请求(我意识到有一个 http 包可能会使这更容易,但我想学习如何使用 dart:io 来做到这一点)。我下面的代码成功地从 example.com 打印出 index.html,除了程序永远运行之外,我假设是因为它继续侦听响应中的数据。从流中接收到所有数据后,如何停止侦听器?我假设我需要将处理程序传递给 onDone 参数,但我不确定是什么。我试着按照下面的方式调用 response.detachSocket(),因为这是我能找到的唯一合乎逻辑的东西,但它没有用。如果不是很明显,我不完全确定我在这里做什么,因此任何解释将不胜感激。

import 'dart:convert';
import 'dart:io';

main() async {
  var client = new HttpClient();
  var request = await client.getUrl(Uri.parse("http://www.example.com/"));
  var response = await request.close();
  response.transform(utf8.decoder).listen((data) {
    print(data);
  },onDone: () => response.detachSocket());
}

解决方法

您从不关闭 HttpClient。完成后关闭它。流订阅将在完成后自行关闭,onDone 处理程序是一种在流完成时运行代码的便捷方式,没有必要使用它来关闭流。

import 'dart:convert';
import 'dart:io';

main() async {
  var client = new HttpClient();
  var request = await client.getUrl(Uri.parse("http://www.example.com/"));
  var response = await request.close();
  response.transform(utf8.decoder).listen((data) {
    print(data);
  },onDone: () => response.detachSocket());
  client.close();
}

也无需拆下插座。


您甚至可以提前调用 client.close,并将 force 参数设置为 false,这是默认值:

main() async {
  var client = new HttpClient();
  var request = await client.getUrl(Uri.parse("http://www.example.com/"));
  client.close();
  var response = await request.close();
  response.transform(utf8.decoder).listen((data) {
    print(data);
  });
}