streamSearchWithRanks method

Stream<List<Map<String, dynamic>>> streamSearchWithRanks({
  1. required List<String> dataset,
  2. required Stream<String> query,
  3. double? strictThreshold,
  4. double? typoThreshold,
  5. bool? kIsWeb,
})

Stream-based search with ranked results

Implementation

Stream<List<Map<String, dynamic>>> streamSearchWithRanks({
  required List<String> dataset,
  required Stream<String> query,
  double? strictThreshold,
  double? typoThreshold,
  bool? kIsWeb,
}) {
  if (dataset.isEmpty) {
    throw ArgumentError("Dataset cannot be empty.");
  }

  _subscription?.cancel(); // Cancel any existing subscription safely
  _subscription = query.listen((inputQuery) async {
    if (inputQuery.trim().isEmpty) {
      // Emit an empty list for empty queries
      if (!_controller.isClosed) {
        _controller.add([]);
      }
      throw ArgumentError("Query cannot be empty or whitespace.");
    }

    // Cancel any ongoing search before starting a new one
    if (_ongoingSearch != null && !_ongoingSearch!.isCompleted) {
      _ongoingSearch!.complete();
    }
    _ongoingSearch = Completer<void>();

    try {
      final result = await _performSearchWithRanks(
        dataset: dataset,
        query: inputQuery,
        strictThreshold: strictThreshold ?? Constants.defaultStrictThreshold,
        typoThreshold: typoThreshold ?? Constants.defaultTypoThreshold,
        kIsWeb: kIsWeb ?? false,
      );

      if (!_controller.isClosed) {
        _controller.add(result);
      }
    } catch (e, stackTrace) {
      if (!_controller.isClosed) {
        _controller.addError(e, stackTrace);
        rethrow;
      }
    } finally {
      _ongoingSearch?.complete();
    }
  });

  return _controller.stream;
}