You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何限制Dart中同步函数format()的运行时长?

限制DartFormatter.format()的运行时长

Dart的DartFormatter.format()是同步函数,没办法直接强制中断正在运行的格式化操作,但可以通过**Isolate(隔离区)**实现超时限制——把格式化任务放到独立的Isolate中执行,超时就终止这个Isolate,避免主线程被长时间阻塞。

具体实现代码

先封装一个带超时的格式化函数:

import 'dart:isolate';
import 'package:dart_style/dart_style.dart';
import 'dart:async';

Future<String> formatWithTimeout(String code, Duration timeout) async {
  final receivePort = ReceivePort();
  try {
    // 启动新Isolate执行格式化任务
    final isolate = await Isolate.spawn(
      _formatInIsolate,
      _IsolateMessage(receivePort.sendPort, code),
    );

    // 设置超时等待结果
    final result = await receivePort.first.timeout(timeout);
    isolate.kill(); // 任务完成后主动销毁Isolate
    if (result is Exception) throw result;
    return result as String;
  } on TimeoutException {
    throw Exception('格式化操作超时');
  } catch (e) {
    rethrow;
  } finally {
    receivePort.close();
  }
}

// 用于Isolate间传递数据的消息类
class _IsolateMessage {
  final SendPort sendPort;
  final String code;

  _IsolateMessage(this.sendPort, this.code);
}

// 在独立Isolate中执行的格式化逻辑
void _formatInIsolate(_IsolateMessage message) {
  try {
    final formattedCode = DartFormatter().format(message.code);
    message.sendPort.send(formattedCode);
  } catch (e) {
    message.sendPort.send(Exception('格式化失败:$e'));
  }
}

使用示例

void main() async {
  final largeStr = '你的超大内容字符串';
  final targetCode = '''
main() {
  $largeStr;
}
''';

  try {
    // 设置5秒超时阈值
    final formatted = await formatWithTimeout(targetCode, const Duration(seconds: 5));
    print('格式化完成:$formatted');
  } catch (e) {
    print('处理失败:$e');
  }
}

关键说明

  1. Isolate是Dart的轻量级执行线程,和主线程完全隔离,主线程可以通过kill()方法强制终止它,以此中断耗时的格式化操作。
  2. 通过ReceivePort和SendPort在Isolate之间传递数据,完成结果或错误的回传。
  3. Isolate间传递大字符串会有一定开销,但相比无限等待主线程阻塞,这种开销完全可接受。

内容的提问来源于stack exchange,提问作者normidar

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.21 07:43:14