Я работаю над пакетом компоновщика и хотел бы получить доступ к имени класса, определенному как суперограничение. При первой сборке его не будет, поэтому я предполагаю, что source_gen просто исключает его из своего анализа.
Например, учитывая, что я требую, чтобы пользователь определил
@fireproof
class User extends _$User {
final UserBase data;
User({
required this.data,
required DocumentSnapshot snapshot,
}) : super(snapshot);
factory User.fromSnapshot(DocumentSnapshot snapshot) =>
_$UserFromSnapshot(snapshot);
}
Как мне узнать имя еще не определенного класса _$User? Я хочу быть динамичным, поэтому, даже если пользователь решит назвать это как-нибудь еще, я смогу адаптироваться к этому имени.
Я пробовал большинство полей этого элемента, но не могу найти ничего, что могло бы дать мне это:
@override
FutureOr<String> generateForAnnotatedElement(
Element element,
ConstantReader annotation,
BuildStep buildStep,
) async {
final classElement = element as ClassElement;
classElement.supertype; // Object
classElement.displayName; // class User
// I want _$User somehow
}
Может быть, ответ заключается в том, чтобы получить астрономию, но я не слишком опытен в этом.





Я копался в freezed и нашел вспомогательную функцию, которая позволяет вам получить узел ast элемента.
Future<AstNode> tryGetAstNodeForElement(
Element element,
BuildStep buildStep,
) async {
var library = element.library!;
while (true) {
try {
return library.session
.getParsedLibraryByElement(library)
.getElementDeclaration(element)!
.node;
} on InconsistentAnalysisException {
library = await buildStep.resolver.libraryFor(
await buildStep.resolver.assetIdForElement(element.library!),
);
}
}
}
Используя эту функцию, вы можете создать узел ast, а затем перебрать его дочерние элементы в поисках нужного шаблона. В freezed это выглядит так
Token? equalToken = ast.endToken;
while (true) {
if (equalToken == null ||
equalToken.charOffset < constructor.nameOffset) {
return null;
}
if (equalToken.stringValue == '=>') return null;
if (equalToken.stringValue == '=') {
break;
}
equalToken = equalToken.previous;
}
поэтому они просматривают токены в обратном порядке, пока не обнаруживают, что токен равен токену, который они хотят (равный токен, который они затем используют для получения перенаправленного конструктора).
В моем случае я бы просто искал закрывающий и открывающий <> для типов и сохранял внутренние типы как строку. AST не игнорирует неопределенные токены.
Вся заслуга Реми Русселе и его посылке.
Убедитесь, что вы используете
.lexemeвместо.stringValue, если вы ищете StringTokens