collectSymbols function
Walks root and returns every top-level and class-member declaration.
Implementation
List<SymbolInfo> collectSymbols(ASTRoot root) {
final out = <SymbolInfo>[];
// Top-level functions.
for (final set in root.functions) {
for (final f in set.functions) {
out.add(
_invocable(f, container: null, category: SymbolCategory.function),
);
}
}
// Classes / enums and their members.
for (final clazz in root.classes) {
final isEnum = clazz is ASTClassEnum;
out.add(
SymbolInfo(
name: clazz.name,
category: isEnum ? SymbolCategory.enumSym : SymbolCategory.classSym,
signature: _classSignature(clazz),
typeName: clazz.name,
modifiers: clazz.isAbstract ? const ['abstract'] : const [],
),
);
for (final field in clazz.fields) {
out.add(
SymbolInfo(
name: field.name,
category: SymbolCategory.field,
container: clazz.name,
signature: '${_typeName(field.type)} ${field.name}',
typeName: _typeName(field.type),
modifiers: field.modifiers.modifiers,
),
);
}
for (final set in clazz.constructors) {
for (final c in set.functions) {
out.add(
_invocable(
c,
container: clazz.name,
category: SymbolCategory.constructor,
),
);
}
}
for (final set in clazz.functions) {
for (final m in set.functions) {
out.add(
_invocable(m, container: clazz.name, category: SymbolCategory.method),
);
}
}
for (final g in clazz.getter) {
out.add(
SymbolInfo(
name: g.name,
category: SymbolCategory.getter,
container: clazz.name,
signature: '${_typeName(g.returnType)} get ${g.name}',
typeName: _typeName(g.returnType),
modifiers: g.modifiers.modifiers,
),
);
}
if (clazz is ASTClassEnum) {
for (final e in clazz.entries) {
out.add(
SymbolInfo(
name: e.name,
category: SymbolCategory.enumMember,
container: clazz.name,
signature: '${clazz.name}.${e.name}',
typeName: clazz.name,
),
);
}
}
}
// Extensions and their members. An unnamed extension has no symbol of its
// own, but its members are still listed, contained by the extended type.
for (final extension in root.extensions) {
final targetName = extension.targetType.name;
final container = extension.name ?? targetName;
if (extension.name != null) {
out.add(
SymbolInfo(
name: extension.name!,
category: SymbolCategory.classSym,
signature: 'extension ${extension.name} on $targetName',
typeName: targetName,
),
);
}
for (final set in extension.functions) {
for (final m in set.functions) {
out.add(
_invocable(m, container: container, category: SymbolCategory.method),
);
}
}
for (final g in extension.getter) {
out.add(
SymbolInfo(
name: g.name,
category: SymbolCategory.getter,
container: container,
signature: '${_typeName(g.returnType)} get ${g.name}',
typeName: _typeName(g.returnType),
modifiers: g.modifiers.modifiers,
),
);
}
}
return out;
}