Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Foreign key references could not be found in any import warning (when upgrading Drift 2.1.0 -> 2.4+) #2433

Closed
pattersonjack opened this issue May 22, 2023 · 2 comments

Comments

@pattersonjack
Copy link

pattersonjack commented May 22, 2023

We've been using custom constraints on several of our tables to add composite foreign keys for some time without issue. However, when attemping to upgrade Drift, new builds display the following warning(s) for all tables that use these constraints:

[WARNING] drift_dev on lib/data/database/tables/video.dart:
line 39, column 5 of package:xxxxxxxxxxxxxxx/data/database/tables/video.dart: `topics` could not be found in any import.
   ╷
39 │ ┌     'FOREIGN KEY (topic_id, topic_lang) REFERENCES '
40 │ │         'topics (id, lang_code)',
   │ └────────────────────────────────^
   ╵

Here is the table that generated the above warning (unsplitting the constraint string results in the same):

import 'package:drift/drift.dart';
import 'package:equatable/equatable.dart';

@DataClassName("Video")
class Videos extends Table implements Equatable {

  IntColumn get id => integer()();

  TextColumn get title => text().nullable()();

  TextColumn get url => text()();

  /// ID of topic the video is in
  IntColumn get topicId => integer()();

  /// Language of the topic the video is in
  TextColumn get topicLang => text()();

  @override
  Set<Column> get primaryKey => {id};

  @override
  List<Object?> get props => [id];

  @override
  bool? get stringify => false;

  @override
  List<String> get customConstraints => [
    'FOREIGN KEY (topic_id, topic_lang) REFERENCES '
        'topics (id, lang_code)',
  ];
}

Below is the Topic table that the Video table (and others) could previously find without issue. This class itself also cannot find the categories table either, but the standard reference to Languages works fine.

import 'package:drift/drift.dart';
import 'package:equatable/equatable.dart';

import 'tables.dart';

@DataClassName("Topic")
class Topics extends Table implements Equatable {

  IntColumn get id => integer()();

  TextColumn get langCode => text().references(Languages, #code)();

  /// Id of the category the topic is in
  IntColumn get categoryId => integer()();

  /// Language of the category the topic is in
  TextColumn get categoryLang => text()();

  TextColumn get title => text()();

  BoolColumn get isSubTopic => boolean()();

  IntColumn get sequenceNumber => integer().nullable()();

  BoolColumn get isFavourited => boolean().withDefault(const Constant(false))();

  /// Current version number for this topic (and all of its content)
  IntColumn get version => integer()();

  /// Composite primary key for the table
  @override
  Set<Column> get primaryKey => {id, langCode};

  @override
  List<Object?> get props => [id, langCode];

  @override
  bool? get stringify => false;

  @override
  List<String> get customConstraints => [
    'FOREIGN KEY (category_id, category_lang) REFERENCES '
        'categories (id, lang_code)',
  ];
}

We've tried adding various imports (e.g. to other tables and/or the main Drift database class) into each table to no avail.

@pattersonjack
Copy link
Author

pattersonjack commented May 22, 2023

Here is a minimal example:

testdb.dart

import 'dart:io';

import 'package:drift/drift.dart';
import 'package:drift/native.dart';
import 'package:path_provider/path_provider.dart';
import 'package:path/path.dart' as p;
import 'tables.dart';

part 'testdb.g.dart';

@DriftDatabase(tables: [Topics, Languages, Videos])
class MyDatabase extends _$MyDatabase {

  MyDatabase() : super(_openConnection());
  
  @override
  int get schemaVersion => 1;
}

LazyDatabase _openConnection() {
  return LazyDatabase(() async {
    final dbFolder = await getApplicationDocumentsDirectory();
    final file = File(p.join(dbFolder.path, 'db.sqlite'));
    return NativeDatabase.createInBackground(file);
  });
}

tables.dart

export 'language.dart';
export 'topic.dart';
export 'video.dart';

language.dart

import 'package:drift/drift.dart';

@DataClassName("Language")
class Languages extends Table {

  TextColumn get code => text()();

  TextColumn get name => text()();

  @override
  Set<Column> get primaryKey => {code};
}

topic.dart

import 'package:drift/drift.dart';

import 'language.dart';

@DataClassName("Topic")
class Topics extends Table {

  IntColumn get id => integer()();

  TextColumn get langCode => text().references(Languages, #code)();

  IntColumn get categoryId => integer()();

  TextColumn get categoryLang => text()();

  TextColumn get title => text()();

  BoolColumn get isSubTopic => boolean()();

  IntColumn get sequenceNumber => integer().nullable()();

  BoolColumn get isFavourited => boolean().withDefault(const Constant(false))();

  IntColumn get version => integer()();

  @override
  Set<Column> get primaryKey => {id};
}

video.dart

import 'package:drift/drift.dart';

import 'topic.dart';
// import 'tables.dart';

@DataClassName("Video")
class Videos extends Table {
  IntColumn get id => integer()();

  TextColumn get title => text().nullable()();

  TextColumn get url => text()();

  IntColumn get topicId => integer()();

  TextColumn get topicLang => text()();

  @override
  Set<Column> get primaryKey => {id};

  @override
  List<String> get customConstraints => [
    'FOREIGN KEY (topic_id, topic_lang) REFERENCES topics (id, lang_code)',
  ];
}

This will generate the following error in Drift 2.4+, but is fine in 2.1.0:

line 22, column 5 of package:test/video.dart: `topics` could not be found in any import.
   ╷
22 │     'FOREIGN KEY (topic_id, topic_lang) REFERENCES topics (id, lang_code)',
   │     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
   ╵

@simolus3
Copy link
Owner

Thanks for the report and for the helpful example!

First, you can safely ignore the error - the only reason it's there now is because older drift versions didn't try to analyze the constraints at all, but it doesn't have any impact on the generated code.

The direct import in your example should work with 451bc9c, so this will be fixed in the next drift_dev version. Importing tables.dart (with the export) will not make the table visible though, I think that'd be a lot more complicated to implement in drift_dev.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants