什么可能导致以下错误?
uncaught exception: SqliteException (SQLite3 returned ErrorConstraint while attempting to perform step.)
奇怪的是,大多数规范都因使用withApp
的错误而失败。
但是,如果我修改wipeDB
中的TestImport.hs
来执行
system "rm project-name_test.sqlite3*"
然后突然所有规格再次通过。虽然测试运行时间大约是4-5倍,但不太理想。
可能是wipeDB
逻辑(由stack new
生成)不够彻底吗?
我试图查看models
文件,看看我是否在其中指定了唯一性限制,但我看不到任何不合适的地方。
我评论了models
以外的所有内容,除了:
User
emailAddress Text
password ByteString
verified Bool
verifyKey Text
resetPasswordKey Text
deriving Show
Foo
userA UserId
userB UserId
deriving Show
如果有限制,他们会在这个文件中,不是吗?或者可以有其他地方宣布约束?无论如何,例外可能涉及哪些约束?
我还没有像我希望的那样缩小范围,但似乎所有这些都可以追溯到runDB $ insert $ Foo
,如果我删除,那么有关的例外就消失了,更多的规格通过,只有少数失败,因为他们希望插入已经发生。它们也因断言失败而失败,而不是ErrorConstraint异常。
如果此错误有多种可能原因,我希望听到这些错误,因为我发现异常比我更加模糊。
答案 0 :(得分:2)
This是我找到的最佳解决方案。看起来像是“官方”解决方案。
所以在我的项目中我完成了this way。
所以现在这是我的wipeDB功能:
wipeDB :: App -> IO ()
wipeDB app = do
let settings = appSettings app
logFunc = messageLoggerSource app (appLogger app)
sqliteConn <- rawConnection (sqlDatabase $ appDatabaseConf settings)
let infoNoFK = set fkEnabled False $ mkSqliteConnectionInfo ""
wrapper = wrapConnectionInfo infoNoFK sqliteConn
pool <- runLoggingT (createSqlPool wrapper 1) logFunc
flip runSqlPersistMPool pool $ do
tables <- getTables
sqlBackend <- ask
let queries = map (\t -> "DELETE FROM " ++ (connEscapeName sqlBackend $ DBName t)) tables
forM_ queries (\q -> rawExecute q [])