1
0
Fork 0
mirror of https://code.sup39.dev/repos/Wqawg synced 2024-12-28 07:34:53 +09:00

Adapt to persistent-migration changes

We have gained:

* Haskell-side validation of schema changes before their execution
* Report of results of migration process
* Handling of old deployments

However:

* The validation code hasn't been tested yet at all
* Most of the migration list hasn't been applied at all yet
* Adding lists of entities from a model file is NOT VALIDATED!!! It's totally
  possible to implement, just need to catch all the small details right
This commit is contained in:
fr33domlover 2018-03-31 19:22:37 +00:00
parent b885ffa075
commit c5a50c336e
3 changed files with 51 additions and 28 deletions

View file

@ -31,7 +31,7 @@ module Vervis.Application
where where
import Control.Concurrent (forkIO) import Control.Concurrent (forkIO)
import Control.Monad.Logger (liftLoc, runLoggingT) import Control.Monad.Logger (liftLoc, runLoggingT, logInfo, logError)
import Database.Persist.Postgresql (createPostgresqlPool, pgConnStr, import Database.Persist.Postgresql (createPostgresqlPool, pgConnStr,
pgPoolSize, runSqlPool) pgPoolSize, runSqlPool)
import Vervis.Import import Vervis.Import
@ -115,7 +115,15 @@ makeFoundation appSettings = do
-- Perform database migration using our application's logging settings. -- Perform database migration using our application's logging settings.
--runLoggingT (runSqlPool (runMigration migrateAll) pool) logFunc --runLoggingT (runSqlPool (runMigration migrateAll) pool) logFunc
runLoggingT (runSqlPool migrateDB pool) logFunc flip runLoggingT logFunc $
flip runSqlPool pool $ do
r <- migrateDB
case r of
Left err -> do
let msg = "DB migration failed: " <> msg
$logError msg
error msg
Right (_from, _to) -> $logInfo "DB migration success"
-- Return the foundation -- Return the foundation
return $ mkFoundation pool return $ mkFoundation pool

View file

@ -30,29 +30,39 @@ import Data.Maybe (fromMaybe, listToMaybe)
import Data.Proxy import Data.Proxy
import Data.Text (Text) import Data.Text (Text)
import Database.Persist import Database.Persist
import Database.Persist.BackendDataType (backendDataType)
import Database.Persist.Migration import Database.Persist.Migration
import Database.Persist.Schema import Database.Persist.Schema (SchemaT, Migration)
import Database.Persist.Schema.Types
import Database.Persist.Schema.PostgreSQL (schemaBackend) import Database.Persist.Schema.PostgreSQL (schemaBackend)
import Database.Persist.Sql (SqlBackend, toSqlKey) import Database.Persist.Sql (SqlBackend, toSqlKey)
import Web.PathPieces (toPathPiece) import Web.PathPieces (toPathPiece)
import qualified Database.Persist.Schema as U (addEntity, unsetFieldDefault)
import Vervis.Migration.Model import Vervis.Migration.Model
import Vervis.Model import Vervis.Model
import Vervis.Model.Ident import Vervis.Model.Ident
import Vervis.Model.Workflow import Vervis.Model.Workflow
changes :: MonadIO m => [SchemaT SqlBackend m ()] type Apply m = SchemaT SqlBackend m ()
type Mig m = Migration SqlBackend m
withPrepare :: Monad m => Mig m -> Apply m -> Mig m
withPrepare (validate, apply) prepare = (validate, prepare >> apply)
changes :: MonadIO m => [Mig m]
changes = changes =
[ -- 1 [ -- 1
traverse_ addEntity model_2016_08_04 unchecked $ traverse_ U.addEntity model_2016_08_04
-- 2 -- 2
, unsetFieldDefault "Sharer" "created" , unchecked $ U.unsetFieldDefault "Sharer" "created"
-- 3 -- 3
, unsetFieldDefault "Project" "nextTicket" , unchecked $ U.unsetFieldDefault "Project" "nextTicket"
-- 4 -- 4
, unsetFieldDefault "Repo" "vcs" , unchecked $ U.unsetFieldDefault "Repo" "vcs"
-- 5 -- 5
, unsetFieldDefault "Repo" "mainBranch" , unchecked $ U.unsetFieldDefault "Repo" "mainBranch"
-- 6 -- 6
, removeField "Ticket" "done" , removeField "Ticket" "done"
-- 7 -- 7
@ -61,24 +71,27 @@ changes =
(FTPrim $ backendDataType (Proxy :: Proxy Text)) (FTPrim $ backendDataType (Proxy :: Proxy Text))
FieldRequired FieldRequired
-- 8 -- 8
, traverse_ addEntity model_2016_09_01_just_workflow , unchecked $ traverse_ U.addEntity model_2016_09_01_just_workflow
-- 9 -- 9
, traverse_ addEntity model_2016_09_01_rest , unchecked $ traverse_ U.addEntity model_2016_09_01_rest
-- 10 -- 10
, do , let key = fromBackendKey defaultBackendKey :: Key Workflow2016
let key = fromBackendKey defaultBackendKey :: Key Workflow2016 in withPrepare
noProjects <- (addField "Project" (Just $ toPathPiece key) $ Field
lift $ null <$> selectKeysList [] [LimitTo 1 :: SelectOpt Project] "workflow"
unless noProjects $ lift $ do (FTRef "Workflow")
msid <- listToMaybe <$> selectKeysList [] [Asc SharerId, LimitTo 1] FieldRequired
for_ msid $ \ sid -> do ) $ do
let ident = text2wfl "dummy" noProjects <- lift $
w = Workflow2016 sid ident Nothing Nothing WSPublic null <$> selectKeysList [] [LimitTo 1 :: SelectOpt Project]
insertKey key w unless noProjects $ lift $ do
addField "Project" (Just $ toPathPiece key) $ Field msid <-
"workflow" listToMaybe <$>
(FTRef "Workflow") selectKeysList [] [Asc SharerId, LimitTo 1]
FieldRequired for_ msid $ \ sid -> do
let ident = text2wfl "dummy"
w = Workflow2016 sid ident Nothing Nothing WSPublic
insertKey key w
-- 11 -- 11
, addField "Workflow" , addField "Workflow"
(Just "'WSSharer'") (Just "'WSSharer'")
@ -114,5 +127,7 @@ changes =
, renameField "Person" "hash" "passphraseHash" , renameField "Person" "hash" "passphraseHash"
] ]
migrateDB :: MonadIO m => ReaderT SqlBackend m () migrateDB :: MonadIO m => ReaderT SqlBackend m (Either Text (Int, Int))
migrateDB = runMigrations schemaBackend changes migrateDB =
let f cs = fmap (, length cs) <$> runMigrations schemaBackend 1 cs
in f changes

View file

@ -27,7 +27,7 @@ import Prelude
import Data.ByteString (ByteString) import Data.ByteString (ByteString)
import Data.Text (Text) import Data.Text (Text)
import Data.Time (UTCTime) import Data.Time (UTCTime)
import Database.Persist.Schema (Entity) import Database.Persist.Schema.Types (Entity)
import Database.Persist.Schema.SQL () import Database.Persist.Schema.SQL ()
import Database.Persist.Sql (SqlBackend) import Database.Persist.Sql (SqlBackend)