roots method

RecursiveMap roots()

Implementation

RecursiveMap roots() {
  if (where((e) => e.access.isEmpty) case final items when items.isNotEmpty) {
    if (items.length == 1) {
      return RecursiveMap();
    }

    if (items.length > 1) {
      if (!items.every(
        (e) => e.type.nonNullName == items.first.type.nonNullName,
      )) {
        throw Exception('Cannot have multiple roots with different types');
      }

      return RecursiveMap();
    }
  }

  final uniquePathsToTypes = <String, String>{};
  for (final e in this) {
    if (e.access.isEmpty) {
      continue;
    }

    if (uniquePathsToTypes[e.access.join('.')] case final type?) {
      if (type != e.type.name) {
        throw Exception('Cannot have multiple roots with different types');
      }
    }

    uniquePathsToTypes[e.access.join('.')] = e.type.name;
  }

  final roots = RecursiveMap();
  if (isEmpty) return roots;

  final sorted = toList().sortedBy<num>((e) => e.access.length).toList();

  final maxLength = sorted.first.access.length;
  var skip = 0;
  for (final ClientParam(:access) in sorted) {
    if (access.length != maxLength) {
      break;
    }

    roots[access.first] = access.skip(1);

    skip++;
  }

  for (final ClientParam(:access) in sorted.skip(skip)) {
    RecursiveMap? current = roots;
    for (final (index, segment) in access.indexed) {
      if (current?[segment] == null) {
        if (index == 0) {
          current?[segment] = access.skip(1);
          break;
        } else {
          break;
        }
      }

      current?[segment] = null;
      current = current?[segment];
    }
  }

  return roots;
}