WebからHDBCを使ってSqliteに書き込む場合のエラー
ハマった。
エラーメッセージは
unable to open database file
で、単純にディレクトリの書き込み権限の問題だったわけだけれど、このエラーメッセージを出すまでがハマった。
HDBCのrun関数では
SQL logic error or missing database
というエラーだけ表示されていて、まともなエラーメッセージを受け取るにはcatchSqlを二重にしてfinish statementでエラーを受け取らないとダメぽい。
inserttable :: (IConnection c) => c -> IO () inserttable dbh = do sth <- prepare dbh "insert into foo(name) values(?)" catchSql (do execute sth [toSql "fred"] commit dbh ) (\ e@(SqlError _ _ m) -> do rollback dbh finish sth `catchSql` \x@(SqlError _ _ m2) -> putStrLn ("insertable: error is " ++ show e ++ "\ninsertable part2: error is " ++ show x) ) -- insertable: error is SqlError {seState = "", seNativeError = 1 -- , seErrorMsg = "step: SQL logic error or missing database"} -- insertable part2: error is SqlError {seState = "", seNativeError = 19 -- , seErrorMsg = "finish: column name is not unique"}jasani.org: Haskell, HDBC and SQLite
まぁ取り敢えずこれでWebから日本語をSqliteに登録できた。
Webサーバの環境変数にUTF-8を設定しない場合は、フォームから来た文字列(UTF-8)を ByteStringでpackしてdecodeStringしてtoSqlに渡すと上手いことやってくれる。
# LANGを定義していないとき、ファイルにはpackしないとマルチバイトが書き込めないが、Sqliteはpackしなくても書き込める…?