如何使用 GRDB 在 iOS 上查询具有 1-1 关联的 table?

How to query a table with a 1-1 association on iOS using GRDB?

在我的 iOS 项目中,我使用 GRDB 来管理 SQLite 数据库。我尝试查询具有 1-1 关联的 table。

在我的数据库中,假设我有 2 tables:

Selections
----------
- selectionId (primary key)
- position
- idSong (foreign key)

Songs
-----
- songId (primary key)
- name
- artist

由于 idSong.

,这两个实体以 1-1 关联关联

这是我尝试过的:

class Selection : Record
{
    var selectionId: Int64?
    var position: Int?
    var idSong: Int64?

    static let song = hasOne(Song.self, key: "selectionId", using: ForeignKey(["songId"]))
    var song: QueryInterfaceRequest<Song> {
        request(for: Selection.song)
    }

    // ...
}
class Song : Record
{
    var songId: Int64?
    var name: String?
    var artist: String?

    static let selection = belongsTo(Selection.self)
    var selection: QueryInterfaceRequest<Selection> {
        request(for: Song.selection)
    }

    // ...
}
struct SelectionSong : FetchableRecord
{
    let selection: Selection
    let song: Song
    
    
    init(row: Row)
    {
        selection = row[Selection.databaseTableName]
        song = row[Song.databaseTableName]
    }
}
    // Selections:
    try db.create(table: Selection.databaseTableName) { table in
        
        table.autoIncrementedPrimaryKey("selectionId")
        table.column("position", .integer).notNull()
        table.column("idSong", .integer)
            .notNull()
            .indexed()
            .references(Song.databaseTableName, onDelete: .cascade)
    }

    // Songs:
    try db.create(table: Song.databaseTableName) { table in
        
        table.autoIncrementedPrimaryKey("songId")
        table.column("name", .text).notNull()
        table.column("artist", .text).notNull()
    }

    let request = Selection.including(optional: Selection.song)
    let list = try SelectionSong.fetchAll(db, request)

但随后出现以下错误:missing scope 'song'

那么我怎样才能查询我的 Selection table,这样我就可以获得 SelectionSong 的列表(一个 Selection 和关联的 Song) ?

谢谢。

以下是需要修复的几个错误:

  • Selectionclass:
class Selection : Record
{
    var selectionId: Int64?
    var position: Int?
    var idSong: Int64?

    static let song = hasOne(Song.self, using: ForeignKey(["songId"], to: ["idSong"]))
    var song: QueryInterfaceRequest<Song> {
        request(for: Selection.song)
    }

    // ...
}
  • Songclass中去掉无用的代码,所以我们得到:
class Song : Record
{
    var songId: Int64?
    var name: String?
    var artist: String?

    // ...
}
  • 最后,在 SelectionSong:
struct SelectionSong : FetchableRecord
{
    let selection: Selection
    let song: Song
    
    
    init(row: Row)
    {
        selection = Selection(row: row)
        song = row["song"]
    }
}

如果您想在 SelectionSong 中使用自定义密钥而不是 "song",请在 Selection 中更改以下内容:

    static let song = hasOne(
        Song.self,
        key: "myCustomKey",
        using: ForeignKey(["songId"], to: ["idSong"]))