Preventing naming conflicts between table columns and existing class fields

This commit is contained in:
Joshua Matthews 2023-09-18 10:20:45 -04:00
parent 8300782662
commit ed1cd9f4e9
No known key found for this signature in database
GPG Key ID: 207AC8D5EABDE954
1 changed files with 37 additions and 4 deletions

View File

@ -71,6 +71,21 @@ class SchemaVersionWriter {
final Map<String, String> _columnCodeToFactory = {}; final Map<String, String> _columnCodeToFactory = {};
final Map<_TableShape, String> _shapes = {}; final Map<_TableShape, String> _shapes = {};
// A list of member names already in use in the generated class. This is used
// to prevent table getters from conflicting with other class members.
final Set<String> _usedNames = {};
void _resetUsedNames() {
_usedNames.clear();
_usedNames.addAll([
'database',
'entities',
'version',
'stepByStepHelper',
'runMigrationSteps',
]);
}
SchemaVersionWriter(this.versions, this.libraryScope) { SchemaVersionWriter(this.versions, this.libraryScope) {
assert(versions.isSortedBy<num>((element) => element.version)); assert(versions.isSortedBy<num>((element) => element.version));
} }
@ -158,9 +173,26 @@ class SchemaVersionWriter {
}); });
} }
String _getNonCollidingGetterName(DriftSchemaElement element) {
var name = element.dbGetterName!;
while (_usedNames.contains(name)) {
name = '$name${_suffixForElement(element)}';
}
_usedNames.add(name);
return name;
}
String _suffixForElement(DriftSchemaElement element) => switch (element) {
DriftTable() => 'Table',
DriftView() => 'View',
DriftIndex() => 'Index',
DriftTrigger() => 'Trigger',
_ => throw ArgumentError('Unhandled element type $element'),
};
String _writeWithResultSet( String _writeWithResultSet(
DriftElementWithResultSet entity, TextEmitter writer) { DriftElementWithResultSet entity, TextEmitter writer) {
final getterName = entity.dbGetterName; final getterName = _getNonCollidingGetterName(entity);
final shape = _shapeClass(entity); final shape = _shapeClass(entity);
writer writer
..write('late final $shape $getterName = ') ..write('late final $shape $getterName = ')
@ -259,7 +291,7 @@ class SchemaVersionWriter {
writer.write('attachedDatabase: database,'); writer.write('attachedDatabase: database,');
writer.write('), alias: null)'); writer.write('), alias: null)');
return getterName!; return getterName;
} }
String _writeEntity({ String _writeEntity({
@ -271,14 +303,14 @@ class SchemaVersionWriter {
if (element is DriftElementWithResultSet) { if (element is DriftElementWithResultSet) {
name = _writeWithResultSet(element, definition); name = _writeWithResultSet(element, definition);
} else if (element is DriftIndex) { } else if (element is DriftIndex) {
name = element.dbGetterName; name = _getNonCollidingGetterName(element);
final index = definition.drift('Index'); final index = definition.drift('Index');
definition definition
..write('final $index $name = ') ..write('final $index $name = ')
..writeln(DatabaseWriter.createIndex(definition.parent!, element)); ..writeln(DatabaseWriter.createIndex(definition.parent!, element));
} else if (element is DriftTrigger) { } else if (element is DriftTrigger) {
name = element.dbGetterName; name = _getNonCollidingGetterName(element);
final trigger = definition.drift('Trigger'); final trigger = definition.drift('Trigger');
definition definition
@ -313,6 +345,7 @@ class SchemaVersionWriter {
final versionNo = version.version; final versionNo = version.version;
final versionClass = '_S$versionNo'; final versionClass = '_S$versionNo';
final versionScope = libraryScope.child(); final versionScope = libraryScope.child();
_resetUsedNames();
// Write an _S<x> class for each schema version x. // Write an _S<x> class for each schema version x.
versionScope.leaf() versionScope.leaf()