ZetCode

Dart HttpServer

最后修改于 2025 年 4 月 4 日

Dart 中的 HttpServer 类提供了创建 HTTP 服务器的功能。它是 dart:io 库的一部分,支持构建 Web 应用程序和 API。

HttpServer 处理传入的 HTTP 请求并管理响应。它支持请求路由、标头和不同的 HTTP 方法等功能。

基本定义

HttpServer 是一个在 Dart 中实现 HTTP 服务器的类。它监听指定端口和地址上的传入 HTTP 请求。

主要功能包括请求处理、响应生成和对持久连接的支持。它构成了 Dart 中 Web 应用程序的基础。

基本的 HttpServer 示例

此示例展示了一个响应所有请求的简单 HTTP 服务器。

main.dart
import 'dart:io';

Future<void> main() async {
  final server = await HttpServer.bind('localhost', 8080);
  print('Server running on http://${server.address.host}:${server.port}');

  await for (HttpRequest request in server) {
    request.response
      ..headers.contentType = ContentType.text
      ..write('Hello from Dart server!')
      ..close();
  }
}

我们在端口 8080 上的 localhost 上绑定了一个 HttpServer。对于每个请求,我们发送一个简单的文本响应。服务器使用 Futures 异步运行。

$ dart main.dart
Server running on https://:8080

处理不同的路由

此示例演示了 HTTP 服务器中的基本路由处理。

main.dart
import 'dart:io';

Future<void> main() async {
  final server = await HttpServer.bind('localhost', 8080);
  
  await for (HttpRequest request in server) {
    switch (request.uri.path) {
      case '/':
        request.response.write('Home page');
        break;
      case '/about':
        request.response.write('About page');
        break;
      default:
        request.response.statusCode = HttpStatus.notFound;
        request.response.write('Not found');
    }
    await request.response.close();
  }
}

我们检查请求 URI 路径以提供不同的响应。默认情况使用 404 状态码处理未知路由。每个响应都必须关闭。

$ dart main.dart

处理 POST 请求

此示例展示了如何处理 POST 请求和读取请求体。

main.dart
import 'dart:io';
import 'dart:convert';

Future<void> main() async {
  final server = await HttpServer.bind('localhost', 8080);
  
  await for (HttpRequest request in server) {
    if (request.method == 'POST') {
      try {
        final content = await utf8.decoder.bind(request).join();
        final data = jsonDecode(content) as Map;
        request.response.write('Received: ${data['message']}');
      } catch (e) {
        request.response.statusCode = HttpStatus.badRequest;
        request.response.write('Invalid request');
      }
    } else {
      request.response.statusCode = HttpStatus.methodNotAllowed;
      request.response.write('Only POST supported');
    }
    await request.response.close();
  }
}

我们检查请求方法并将 POST 数据作为 JSON 处理。请求体是异步读取的。错误处理确保了稳健的运行。

$ dart main.dart

服务静态文件

此示例演示了如何从目录中服务静态文件。

main.dart
import 'dart:io';

Future<void> main() async {
  final server = await HttpServer.bind('localhost', 8080);
  final staticDir = Directory('static');
  
  await for (HttpRequest request in server) {
    final filePath = 'static${request.uri.path}';
    final file = File(filePath);
    
    if (await file.exists()) {
      await request.response.addStream(file.openRead());
    } else {
      request.response.statusCode = HttpStatus.notFound;
      request.response.write('File not found');
    }
    await request.response.close();
  }
}

我们从与请求路径匹配的“static”目录中服务文件。文件内容直接流式传输到响应中以提高效率。

$ dart main.dart

WebSocket 服务器

此示例展示了如何将 HTTP 连接升级到 WebSocket。

main.dart
import 'dart:io';

Future<void> main() async {
  final server = await HttpServer.bind('localhost', 8080);
  
  await for (HttpRequest request in server) {
    if (WebSocketTransformer.isUpgradeRequest(request)) {
      final socket = await WebSocketTransformer.upgrade(request);
      socket.listen((data) {
        socket.add('Echo: $data');
      });
    } else {
      request.response.statusCode = HttpStatus.badRequest;
      request.response.write('WebSocket expected');
      await request.response.close();
    }
  }
}

我们检查 WebSocket 升级请求并单独处理它们。WebSocket 连接允许与客户端进行双向通信。

$ dart main.dart

最佳实践

来源

Dart HttpServer 文档

本教程介绍了 Dart 的 HttpServer 类,并通过实际示例展示了基本用法、路由处理、POST 处理、静态文件和服务 WebSockets。

作者

我的名字是 Jan Bodnar,我是一名热情的程序员,拥有丰富的编程经验。自 2007 年以来,我一直在撰写编程文章。迄今为止,我已撰写了 1400 多篇文章和 8 本电子书。我在教授编程方面拥有超过十年的经验。

列出 所有 Dart 教程