forked from GitHub/gf-core
error recovery in rename and check grammar: report all errors in a module before terminating
This commit is contained in:
@@ -56,6 +56,11 @@ showCheckModule mos m = do
|
|||||||
(st,(_,msg)) <- checkStart $ checkModule mos m
|
(st,(_,msg)) <- checkStart $ checkModule mos m
|
||||||
return (st, unlines $ reverse msg)
|
return (st, unlines $ reverse msg)
|
||||||
|
|
||||||
|
mapsCheckTree ::
|
||||||
|
(Ord a) => ((a,b) -> Check (a,c)) -> BinTree a b -> Check (BinTree a c)
|
||||||
|
mapsCheckTree f = checkErr . mapsErrTree (\t -> checkStart (f t) >>= return . fst)
|
||||||
|
|
||||||
|
|
||||||
-- | checking is performed in the dependency order of modules
|
-- | checking is performed in the dependency order of modules
|
||||||
checkModule :: [SourceModule] -> SourceModule -> Check [SourceModule]
|
checkModule :: [SourceModule] -> SourceModule -> Check [SourceModule]
|
||||||
checkModule ms (name,mod) = checkIn ("checking module" +++ prt name) $ case mod of
|
checkModule ms (name,mod) = checkIn ("checking module" +++ prt name) $ case mod of
|
||||||
@@ -63,24 +68,24 @@ checkModule ms (name,mod) = checkIn ("checking module" +++ prt name) $ case mod
|
|||||||
ModMod mo@(Module mt st fs me ops js) -> do
|
ModMod mo@(Module mt st fs me ops js) -> do
|
||||||
checkRestrictedInheritance ms (name, mo)
|
checkRestrictedInheritance ms (name, mo)
|
||||||
js' <- case mt of
|
js' <- case mt of
|
||||||
MTAbstract -> mapMTree (checkAbsInfo gr name) js
|
MTAbstract -> mapsCheckTree (checkAbsInfo gr name) js
|
||||||
|
|
||||||
MTTransfer a b -> mapMTree (checkAbsInfo gr name) js
|
MTTransfer a b -> mapsCheckTree (checkAbsInfo gr name) js
|
||||||
|
|
||||||
MTResource -> mapMTree (checkResInfo gr name) js
|
MTResource -> mapsCheckTree (checkResInfo gr name) js
|
||||||
|
|
||||||
MTConcrete a -> do
|
MTConcrete a -> do
|
||||||
checkErr $ topoSortOpers $ allOperDependencies name js
|
checkErr $ topoSortOpers $ allOperDependencies name js
|
||||||
ModMod abs <- checkErr $ lookupModule gr a
|
ModMod abs <- checkErr $ lookupModule gr a
|
||||||
js1 <- checkCompleteGrammar abs mo
|
js1 <- checkCompleteGrammar abs mo
|
||||||
mapMTree (checkCncInfo gr name (a,abs)) js1
|
mapsCheckTree (checkCncInfo gr name (a,abs)) js1
|
||||||
|
|
||||||
MTInterface -> mapMTree (checkResInfo gr name) js
|
MTInterface -> mapsCheckTree (checkResInfo gr name) js
|
||||||
|
|
||||||
MTInstance a -> do
|
MTInstance a -> do
|
||||||
ModMod abs <- checkErr $ lookupModule gr a
|
ModMod abs <- checkErr $ lookupModule gr a
|
||||||
-- checkCompleteInstance abs mo -- this is done in Rebuild
|
-- checkCompleteInstance abs mo -- this is done in Rebuild
|
||||||
mapMTree (checkResInfo gr name) js
|
mapsCheckTree (checkResInfo gr name) js
|
||||||
|
|
||||||
return $ (name, ModMod (Module mt st fs me ops js')) : ms
|
return $ (name, ModMod (Module mt st fs me ops js')) : ms
|
||||||
|
|
||||||
|
|||||||
@@ -58,7 +58,7 @@ renameModule ms (name,mod) = errIn ("renaming module" +++ prt name) $ case mod o
|
|||||||
ModMod m@(Module mt st fs me ops js) -> do
|
ModMod m@(Module mt st fs me ops js) -> do
|
||||||
let js1 = jments m
|
let js1 = jments m
|
||||||
status <- buildStatus (MGrammar ms) name mod
|
status <- buildStatus (MGrammar ms) name mod
|
||||||
js2 <- mapMTree (renameInfo status) js1
|
js2 <- mapsErrTree (renameInfo status) js1
|
||||||
let mod2 = ModMod $ Module mt st fs me (map forceQualif ops) js2
|
let mod2 = ModMod $ Module mt st fs me (map forceQualif ops) js2
|
||||||
return $ (name,mod2) : ms
|
return $ (name,mod2) : ms
|
||||||
|
|
||||||
|
|||||||
@@ -22,7 +22,7 @@ module GF.Data.Operations (-- * misc functions
|
|||||||
performOps, repeatUntilErr, repeatUntil, okError, isNotError,
|
performOps, repeatUntilErr, repeatUntil, okError, isNotError,
|
||||||
showBad, lookupErr, lookupErrMsg, lookupDefault, updateLookupList,
|
showBad, lookupErr, lookupErrMsg, lookupDefault, updateLookupList,
|
||||||
mapPairListM, mapPairsM, pairM, mapErr, mapErrN, foldErr,
|
mapPairListM, mapPairsM, pairM, mapErr, mapErrN, foldErr,
|
||||||
(!?), errList, singleton,
|
(!?), errList, singleton, mapsErr, mapsErrTree,
|
||||||
|
|
||||||
-- ** checking
|
-- ** checking
|
||||||
checkUnique, titleIfNeeded, errMsg, errAndMsg,
|
checkUnique, titleIfNeeded, errMsg, errAndMsg,
|
||||||
@@ -183,6 +183,7 @@ mapErrN maxN f xs = Ok (ys, unlines (errHdr : ss2))
|
|||||||
nss = length ss
|
nss = length ss
|
||||||
fxs = map f xs
|
fxs = map f xs
|
||||||
|
|
||||||
|
|
||||||
-- | like @foldM@, but also return the latest value if fails
|
-- | like @foldM@, but also return the latest value if fails
|
||||||
foldErr :: (a -> b -> Err a) -> a -> [b] -> Err (a, Maybe String)
|
foldErr :: (a -> b -> Err a) -> a -> [b] -> Err (a, Maybe String)
|
||||||
foldErr f s xs = case xs of
|
foldErr f s xs = case xs of
|
||||||
@@ -630,6 +631,23 @@ instance ErrorMonad (STM s) where
|
|||||||
`handle` (\e -> let STM g' = (g e) in
|
`handle` (\e -> let STM g' = (g e) in
|
||||||
g' s))
|
g' s))
|
||||||
|
|
||||||
|
-- error recovery with multiple reporting AR 30/5/2008
|
||||||
|
mapsErr :: (a -> Err b) -> [a] -> Err [b]
|
||||||
|
|
||||||
|
mapsErr f = seqs . map f where
|
||||||
|
seqs es = case es of
|
||||||
|
Ok v : ms -> case seqs ms of
|
||||||
|
Ok vs -> return (v : vs)
|
||||||
|
b -> b
|
||||||
|
Bad s : ms -> case seqs ms of
|
||||||
|
Ok vs -> Bad s
|
||||||
|
Bad ss -> Bad (s +++++ ss)
|
||||||
|
[] -> return []
|
||||||
|
|
||||||
|
mapsErrTree :: (Ord a) => ((a,b) -> Err (a,c)) -> BinTree a b -> Err (BinTree a c)
|
||||||
|
mapsErrTree f t = mapsErr f (tree2list t) >>= return . sorted2tree
|
||||||
|
|
||||||
|
|
||||||
-- | if the first check fails try another one
|
-- | if the first check fails try another one
|
||||||
checkAgain :: ErrorMonad m => m a -> m a -> m a
|
checkAgain :: ErrorMonad m => m a -> m a -> m a
|
||||||
checkAgain c1 c2 = handle_ c1 c2
|
checkAgain c1 c2 = handle_ c1 c2
|
||||||
|
|||||||
Reference in New Issue
Block a user