@@ -40,15 +40,11 @@ module Database.Beam.Migrate.Types
40
40
, MigrationCommand (.. ), MigrationDataLoss (.. )
41
41
42
42
, runMigrationSteps , runMigrationSilenced
43
- , runMigrationVerbose , executeMigration
44
- , eraseMigrationType , migrationStep , upDown
45
- , migrationDataLoss
43
+ , executeMigration , eraseMigrationType , migrationStep
44
+ , upDown , migrationDataLoss
46
45
47
46
, migrateScript , evaluateDatabase , stepNames ) where
48
47
49
- import Database.Beam
50
- import Database.Beam.Backend
51
-
52
48
import Database.Beam.Migrate.Types.CheckedEntities
53
49
import Database.Beam.Migrate.Types.Predicates
54
50
@@ -61,19 +57,27 @@ import Data.Text (Text)
61
57
62
58
-- * Migration types
63
59
60
+ -- | Represents a particular step in a migration
64
61
data MigrationStep syntax next where
65
62
MigrationStep :: Text -> Migration syntax a -> (a -> next ) -> MigrationStep syntax next
66
63
deriving instance Functor (MigrationStep syntax )
64
+
65
+ -- | A series of 'MigrationStep's that take a database from the schema in @from@
66
+ -- to the one in @to@. Use the 'migrationStep' function and the arrow interface
67
+ -- to sequence 'MigrationSteps'.
67
68
newtype MigrationSteps syntax from to = MigrationSteps (Kleisli (F (MigrationStep syntax )) from to )
68
69
deriving (Category , Arrow )
69
70
71
+ -- | Free monadic function for 'Migration's
70
72
data MigrationF syntax next where
71
73
MigrationRunCommand
72
74
:: { _migrationUpCommand :: syntax {-^ What to execute when applying the migration -}
73
75
, _migrationDownCommand :: Maybe syntax {-^ What to execute when unapplying the migration -}
74
76
, _migrationNext :: next }
75
77
-> MigrationF syntax next
76
78
deriving instance Functor (MigrationF syntax )
79
+
80
+ -- | A sequence of potentially reversible schema update commands
77
81
type Migration syntax = F (MigrationF syntax )
78
82
79
83
-- | Information on whether a 'MigrationCommand' loses data. You can
@@ -101,10 +105,14 @@ data MigrationCommand cmd
101
105
-- ^ Information on whether the migration loses data
102
106
} deriving Show
103
107
108
+ -- | Run the migration steps between the given indices, using a custom execution function.
104
109
runMigrationSteps :: Monad m
105
- => Int -> Maybe Int
106
- -> MigrationSteps syntax () a
110
+ => Int -- ^ Zero-based index of the first step to run
111
+ -> Maybe Int -- ^ Index of the last step to run, or 'Nothing' to run every step
112
+ -> MigrationSteps syntax () a -- ^ The set of steps to run
107
113
-> (forall a' . Int -> Text -> Migration syntax a' -> m a' )
114
+ -- ^ Callback for each step. Called with the step index, the
115
+ -- step description and the migration.
108
116
-> m a
109
117
runMigrationSteps firstIdx lastIdx (MigrationSteps steps) runMigration =
110
118
runF (runKleisli steps () ) finish step 0
@@ -114,33 +122,37 @@ runMigrationSteps firstIdx lastIdx (MigrationSteps steps) runMigration =
114
122
then runMigration i nm doStep >>= \ x -> next x (i + 1 )
115
123
else next (runMigrationSilenced doStep) (i + 1 )
116
124
125
+ -- | Get the result of a migration, without running any steps
117
126
runMigrationSilenced :: Migration syntax a -> a
118
127
runMigrationSilenced m = runF m id step
119
128
where
120
129
step (MigrationRunCommand _ _ next) = next
121
130
122
- runMigrationVerbose :: MonadBeam syntax be hdl m => (syntax -> String )
123
- -> Migration syntax a -> m a
124
- runMigrationVerbose renderMigrationSyntax steps =
125
- runF steps finish step
126
- where finish = pure
127
- step (MigrationRunCommand up _ next) =
128
- do liftIO (putStrLn (renderMigrationSyntax up))
129
- runNoReturn up
130
- next
131
-
131
+ -- | Remove the explicit source and destination schemas from a 'MigrationSteps' object
132
132
eraseMigrationType :: a -> MigrationSteps syntax a a' -> MigrationSteps syntax () ()
133
133
eraseMigrationType a (MigrationSteps steps) = MigrationSteps (arr (const a) >>> steps >>> arr (const () ))
134
134
135
+ -- | Create a 'MigrationSteps' from the given description and migration function.
135
136
migrationStep :: Text -> (a -> Migration syntax a' ) -> MigrationSteps syntax a a'
136
137
migrationStep stepName migration =
137
138
MigrationSteps (Kleisli (\ a -> liftF (MigrationStep stepName (migration a) id )))
138
139
140
+ -- | Given a command in the forward direction, and an optional one in the
141
+ -- reverse direction, construct a 'Migration' that performs the given
142
+ -- command. Multiple commands can be sequenced monadically.
139
143
upDown :: syntax -> Maybe syntax -> Migration syntax ()
140
144
upDown up down = liftF (MigrationRunCommand up down () )
141
145
142
- migrateScript :: forall syntax m a .
143
- Monoid m => (Text -> m ) -> (syntax -> m ) -> MigrationSteps syntax () a -> m
146
+ -- | Given functions to render a migration step description and the underlying
147
+ -- syntax, create a script for the given 'MigrationSteps'.
148
+ migrateScript :: forall syntax m a . Monoid m
149
+ => (Text -> m )
150
+ -- ^ Called at the beginning of each 'MigrationStep' with the step description
151
+ -> (syntax -> m )
152
+ -- ^ Called for each command in the migration step
153
+ -> MigrationSteps syntax () a
154
+ -- ^ The set of steps to run
155
+ -> m
144
156
migrateScript renderMigrationHeader renderMigrationSyntax (MigrationSteps steps) =
145
157
runF (runKleisli steps () ) (\ _ x -> x)
146
158
(\ (MigrationStep header migration next) x ->
@@ -168,16 +180,18 @@ migrationDataLoss go = runF go (\_ -> MigrationKeepsData)
168
180
Nothing -> MigrationLosesData
169
181
_ -> next)
170
182
183
+ -- | Run a 'MigrationSteps' without executing any of the commands against a
184
+ -- database.
171
185
evaluateDatabase :: forall syntax a . MigrationSteps syntax () a -> a
172
186
evaluateDatabase (MigrationSteps f) = runF (runKleisli f () ) id (\ (MigrationStep _ migration next) -> next (runMigration migration))
173
187
where
174
188
runMigration :: forall a' . Migration syntax a' -> a'
175
189
runMigration migration = runF migration id (\ (MigrationRunCommand _ _ next) -> next)
176
190
191
+ -- | Collect the names of all steps in hte given 'MigrationSteps'
177
192
stepNames :: forall syntax a . MigrationSteps syntax () a -> [Text ]
178
193
stepNames (MigrationSteps f) = runF (runKleisli f () ) (\ _ x -> x) (\ (MigrationStep nm migration next) x -> next (runMigration migration) (x ++ [nm])) []
179
194
where
180
195
runMigration :: forall a' . Migration syntax a' -> a'
181
196
runMigration migration = runF migration id (\ (MigrationRunCommand _ _ next) -> next)
182
197
183
- -- * Checked database entities
0 commit comments