未生成 Sqldelight 数据库架构

Posted

技术标签:

【中文标题】未生成 Sqldelight 数据库架构【英文标题】:Sqldelight database schema not generated 【发布时间】:2021-03-10 02:30:33 【问题描述】:

我有一个 KMM 项目并想使用 SqlDelight 库,但是当我构建项目时没有生成数据库架构和表实体。

actual class DatabaseDriverFactory(private val context: Context) 
    actual fun createDriver(): SqlDriver 
               //Unresolved reference: CoreDb
        return androidSqliteDriver(CoreDb.Schema, context, "test.db")
    

我在我的共享模块中定义了 sqldelight 文件夹,还为功能生成的 kotlin 类创建了文件夹,因为它在 gradle.build.kts 中配置,并且在 sqldelight 文件夹中还有一个 *.sq 文件

sqldelight 
  database("CoreDb") 
    packageName = "com.example.app.core.database"
    sourceFolders = listOf("sqldelight")
    dialect = "sqlite:3.24"
  

当我运行 generateSqlDelightInterface 任务时,我只会看到那些日志

> Task :core:generateAndroidDebugCoreDbInterface NO-SOURCE
> Task :core:generateAndroidReleaseCoreDbInterface NO-SOURCE
> Task :core:generateiosMainCoreDbInterface NO-SOURCE
> Task :core:generateMetadataCommonMainCoreDbInterface NO-SOURCE
> Task :core:generateMetadataMainCoreDbInterface NO-SOURCE
> Task :core:generateSqlDelightInterface UP-TO-DATE
can't register checkAndroidModules

BUILD SUCCESSFUL in 311ms
1:40:36 PM: Task execution finished 'generateSqlDelightInterface'.

这是我完整的build.gradle.kts

import org.jetbrains.kotlin.gradle.plugin.mpp.KotlinNativeTarget

plugins 
  kotlin("multiplatform")
  kotlin("plugin.serialization")
  id("com.android.library")
  id("kotlin-android-extensions")
  id("koin")
  id("com.squareup.sqldelight")


repositories 
  gradlePluginPortal()
  google()
  jcenter()
  mavenCentral()
  maven 
    url = uri("https://dl.bintray.com/kotlin/kotlin-eap")
  
  maven 
    url = uri("https://dl.bintray.com/ekito/koin")
  

kotlin 
  android()

  val iOSTarget: (String, KotlinNativeTarget.() -> Unit) -> KotlinNativeTarget =
    if (System.getenv("SDK_NAME")?.startsWith("iphoneos") == true)
      ::iosArm64
    else
      ::iosX64

  iOSTarget("ios") 
    binaries 
      framework 
        baseName = "core"
      
    
  
  val coroutinesVersion = "1.3.9-native-mt"
  val ktor_version = "1.4.2"
  val serializationVersion = "1.0.0-RC"
  val koin_version = "3.0.0-alpha-4"
  val sqlDelight = "1.4.4"

  sourceSets 

    val commonMain by getting 
      dependencies 
        implementation("io.ktor:ktor-client-core:$ktor_version")
        implementation("io.ktor:ktor-client-serialization:$ktor_version")

        implementation("org.jetbrains.kotlinx:kotlinx-coroutines-core:$coroutinesVersion")
        implementation("org.jetbrains.kotlinx:kotlinx-serialization-core:$serializationVersion")


        implementation("com.squareup.sqldelight:runtime:$sqlDelight")
        // SqlDelight extension
        implementation("com.squareup.sqldelight:coroutines-extensions:$sqlDelight")
        // Koin for Kotlin
        implementation("org.koin:koin-core:$koin_version")
        //shared preferences
        implementation("com.russhwolf:multiplatform-settings:0.6.3")
      
    
    val commonTest by getting 
      dependencies 
        implementation(kotlin("test-common"))
        implementation(kotlin("test-annotations-common"))
      
    
    val androidMain by getting 
      dependencies 
        implementation("androidx.core:core-ktx:1.3.2")
        implementation("io.ktor:ktor-client-android:$ktor_version")
        implementation("com.squareup.sqldelight:android-driver:$sqlDelight")
      
    
    val androidTest by getting 
      dependencies 
        implementation(kotlin("test-junit"))
        implementation("junit:junit:4.12")
      
    
    val iosMain by getting 
      dependencies 
        implementation("io.ktor:ktor-client-ios:$ktor_version")
        implementation("com.squareup.sqldelight:native-driver:$sqlDelight")
      
    

  
    val iosTest by getting
  




android 
  compileSdkVersion(29)
  sourceSets["main"].manifest.srcFile("src/androidMain/AndroidManifest.xml")
  defaultConfig 
    minSdkVersion(23)
    targetSdkVersion(29)
    versionCode = 1
    versionName = "1.0"
  
  buildTypes 
    getByName("release") 
      isMinifyEnabled = false
    
  

val packForXcode by tasks.creating(Sync::class) 
  group = "build"
  val mode = System.getenv("CONFIGURATION") ?: "DEBUG"
  val sdkName = System.getenv("SDK_NAME") ?: "iphonesimulator"
  val targetName = "ios" + if (sdkName.startsWith("iphoneos")) "Arm64" else "X64"
  val framework =
    kotlin.targets.getByName<KotlinNativeTarget>("ios").binaries.getFramework(mode)
  inputs.property("mode", mode)
  dependsOn(framework.linkTask)
  val targetDir = File(buildDir, "xcode-frameworks")
  from( framework.outputDirectory )
  into(targetDir)

tasks.getByName("build").dependsOn(packForXcode)


sqldelight 
  database("CoreDb") 
    packageName = "com.example.app.core.database"
    sourceFolders = listOf("sqldelight")
    dialect = "sqlite:3.24"
  

对于***build.gradle

classpath "com.squareup.sqldelight:gradle-plugin:$sqlDelight"

更新

我的项目文件夹结构

root
  app
    src
      ...

  core //(kmm shared module)
    androidMain
        com.example.app.core
            database
    commonMain
        com.example.app.core
            database
            repository
            ...
            sqldelight
    iosMain
        com.example.app.core
            database

【问题讨论】:

能否请您发布您的项目文件夹结构? @shadowsheep 我更新了帖子 sqldelight 文件夹与您的*.sq 文件应直接放在commonMain 我会调查更多 非常感谢,我从昨天开始就在努力解决这个问题 【参考方案1】:

您的 sqldelight 文件夹似乎放错了位置。

应该直接放在commonMain里面,sqldelight里面你必须指定你的包。

其他可能的原因

正如 IgorGanapolsky 指出的那样,同样的问题也可能是由不兼容的 gradle 插件版本引起的。

【讨论】:

我试过了,它说:Task :core:generateAndroidDebugCoreDbInterface FAILED /Users/mrkt/StudioProjects/projectName/core/src/commonMain/sqldelight/User.sq line 1:0 - SqlDelight 文件必须是放在包目录中。 @JemoMgebrishvili 明白了!您必须将包文件夹结构放在文件夹 sqldeglight 中,就像您在 build.gradle.kts:sqldelght 部分中指定的那样。 很好,谢谢,还没有检查。今天会尽快检查一下 这不是导致此类问题的真正问题。 这是我在使用最新的 KMM 和 1.5.3 的 sqldelight 时遇到的问题。它没有说明您需要在 Kotlin 教程中创建这些实际目录。通过创建与提供的 packageName 匹配的目录,您将能够生成您的命名数据库。谢谢@shadowsheep【参考方案2】:

这可能对将来的某人有所帮助...我在 KMM 中创建了一个目录,并将其命名为 sqldelight.com.package.database

我认为这是一个合适的包,但意识到这并没有被 SQLDelight 捕获,因此没有生成我的架构。

我需要将结构创建为正确的目录结构(然后一切正常):

sqldelight
  com
    package
      dataabase

【讨论】:

【参考方案3】:

或者,如果您希望 SQL 代码与您的代码位于同一目录中,您可以将文件夹更改为 kotlin:

sqldelight 
  database("CoreDb") 
    ...
    sourceFolders = listOf("kotlin")
    ...
  

【讨论】:

以上是关于未生成 Sqldelight 数据库架构的主要内容,如果未能解决你的问题,请参考以下文章

typeORM 未发现数据库架构更改 - 无法生成迁移。要创建新的空迁移,请使用“typeorm migration:create”命令

typeorm:migration create on New Project Does Not Recognize Entities - “未发现数据库架构更改 - 无法生成迁移。”

未设置 Pig 架构元组。不会生成代码

无法从 sqldelight v1.4.1 访问生成的数据库类

TypeORM CLI:未发现数据库架构更改

SqlDelight/SQLite 没有正确执行连接?