In-memory Sqlite DB disappears between transactions
See original GitHub issueI have an in-memory sqlite db. The following code yields an error. Here’s the code:
import org.jetbrains.exposed.dao.EntityID
import org.jetbrains.exposed.dao.UUIDEntity
import org.jetbrains.exposed.dao.UUIDEntityClass
import org.jetbrains.exposed.dao.UUIDTable
import org.jetbrains.exposed.sql.*
import org.jetbrains.exposed.sql.transactions.TransactionManager
import org.jetbrains.exposed.sql.transactions.transaction
import photo.backup.kt.data.HashTable
import java.sql.Connection
import java.util.*
object MyTable: UUIDTable() {
val name = varchar("name", 50)
}
class Name(id: EntityID<UUID>): UUIDEntity(id) {
companion object: UUIDEntityClass<Name>(MyTable)
var name by MyTable.name
}
fun main() {
val db = Database.connect("jdbc:sqlite:file:test?mode=memory&cache=shared", "org.sqlite.JDBC")
TransactionManager.manager.defaultIsolationLevel = Connection.TRANSACTION_SERIALIZABLE
transaction(db) {
addLogger(StdOutSqlLogger)
SchemaUtils.create(MyTable)
}
println(UUID.randomUUID())
val id = transaction(db) {
MyTable.insert {
it[name] = "Foo"
} get MyTable.id
}
println(id)
}
main()
Here’s the error:
Exception in thread "main" org.jetbrains.exposed.exceptions.ExposedSQLException: org.sqlite.SQLiteException: [SQLITE_ERROR] SQL error or missing database (no such table: My)
SQL: [INSERT INTO My (id, "name") VALUES (?, ?)]
at org.jetbrains.exposed.sql.statements.Statement.executeIn$exposed_core(Statement.kt:50)
at org.jetbrains.exposed.sql.Transaction.exec(Transaction.kt:122)
at org.jetbrains.exposed.sql.Transaction.exec(Transaction.kt:108)
at org.jetbrains.exposed.sql.statements.Statement.execute(Statement.kt:29)
at org.jetbrains.exposed.sql.QueriesKt.insert(Queries.kt:45)
at org.jetbrains.kotlin.idea.scratch.generated.ScratchFileRunnerGenerated$ScratchFileRunnerGenerated$main$id$1.invoke(tmp.kt:34)
at org.jetbrains.kotlin.idea.scratch.generated.ScratchFileRunnerGenerated$ScratchFileRunnerGenerated$main$id$1.invoke(tmp.kt:16)
at org.jetbrains.exposed.sql.transactions.ThreadLocalTransactionManagerKt$inTopLevelTransaction$1.invoke(ThreadLocalTransactionManager.kt:156)
at org.jetbrains.exposed.sql.transactions.ThreadLocalTransactionManagerKt$inTopLevelTransaction$2.invoke(ThreadLocalTransactionManager.kt:197)
at org.jetbrains.exposed.sql.transactions.ThreadLocalTransactionManagerKt.keepAndRestoreTransactionRefAfterRun(ThreadLocalTransactionManager.kt:205)
at org.jetbrains.exposed.sql.transactions.ThreadLocalTransactionManagerKt.inTopLevelTransaction(ThreadLocalTransactionManager.kt:196)
at org.jetbrains.exposed.sql.transactions.ThreadLocalTransactionManagerKt$transaction$1.invoke(ThreadLocalTransactionManager.kt:134)
at org.jetbrains.exposed.sql.transactions.ThreadLocalTransactionManagerKt.keepAndRestoreTransactionRefAfterRun(ThreadLocalTransactionManager.kt:205)
at org.jetbrains.exposed.sql.transactions.ThreadLocalTransactionManagerKt.transaction(ThreadLocalTransactionManager.kt:106)
at org.jetbrains.exposed.sql.transactions.ThreadLocalTransactionManagerKt.transaction(ThreadLocalTransactionManager.kt:104)
at org.jetbrains.kotlin.idea.scratch.generated.ScratchFileRunnerGenerated$ScratchFileRunnerGenerated.main(tmp.kt:33)
at org.jetbrains.kotlin.idea.scratch.generated.ScratchFileRunnerGenerated$ScratchFileRunnerGenerated.generated_get_instance_res0(tmp.kt:40)
at org.jetbrains.kotlin.idea.scratch.generated.ScratchFileRunnerGenerated.main(tmp.kt:52)
Caused by: org.sqlite.SQLiteException: [SQLITE_ERROR] SQL error or missing database (no such table: My)
at org.sqlite.core.DB.newSQLException(DB.java:909)
at org.sqlite.core.DB.newSQLException(DB.java:921)
at org.sqlite.core.DB.throwex(DB.java:886)
at org.sqlite.core.NativeDB.prepare_utf8(Native Method)
at org.sqlite.core.NativeDB.prepare(NativeDB.java:127)
at org.sqlite.core.DB.prepare(DB.java:227)
at org.sqlite.core.CorePreparedStatement.<init>(CorePreparedStatement.java:41)
chaging Database.connect("jdbc:sqlite:file:test?mode=memory&cache=shared", "org.sqlite.JDBC")
to Database.connect("jdbc:sqlite:/path/to/data.db", "org.sqlite.JDBC")
then the DB is created and the insertion happens correctly
Issue Analytics
- State:
- Created 4 years ago
- Reactions:2
- Comments:18 (3 by maintainers)
Top Results From Across the Web
In-memory SQLite and database disappearing - Stack Overflow
The database ceases to exist as soon as the database connection is closed. " However, this can be worked around with multiple connections...
Read more >Does in memory db behave the same as a normal db - SQLite
I am testing a db application. The best would be to create the database for every test. I timed the creation of a...
Read more >How To Corrupt An SQLite Database File
Failing that, it is safe to make a copy of an SQLite database file as long as there are no transactions in progress...
Read more >File Locking And Concurrency In SQLite Version 3
Obtain an EXCLUSIVE lock on the database file and make sure all memory changes have been written to the database file using the...
Read more >Atomic Commit In SQLite
We begin with an overview of the steps SQLite takes in order to perform an atomic commit of a transaction against a single...
Read more >Top Related Medium Post
No results found
Top Related StackOverflow Question
No results found
Troubleshoot Live Code
Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start FreeTop Related Reddit Thread
Top Related Hackernoon Post
No results found
Top Related Tweet
No results found
Top Related Dev.to Post
No results found
Top Related Hashnode Post
No results found
Top GitHub Comments
Connection pooling with Hikari works. It might be useful to put a note about this in an example for Sqlite in-memory DBs since the docs don’t make it clear that a Sqlite in-memory DB will be destroyed between transactions. Here is sample code for using Hikari connection pooling with a Sqlite in-memory DB:
Now the in-memory DB will not be destroyed between transactions.
I used the following workaround:
As long as you don’t
close()
thekeepAliveConnection
, the Database will persist in memory. Not pretty, but works.