|
19 | 19 | module Language.PureScript.Errors where |
20 | 20 |
|
21 | 21 | import Data.Either (lefts, rights) |
22 | | -import Data.List (intercalate, elemIndex) |
| 22 | +import Data.List (intercalate) |
| 23 | +import Data.Function (on) |
23 | 24 | import Data.Monoid |
24 | 25 | import Data.Foldable (fold, foldMap) |
25 | 26 |
|
| 27 | +import qualified Data.Map as M |
| 28 | + |
26 | 29 | import Control.Monad |
27 | 30 | import Control.Monad.Error.Class (MonadError(..)) |
28 | 31 | import Control.Monad.Unify |
@@ -252,19 +255,22 @@ errorMessage err = MultipleErrors [err] |
252 | 255 | onErrorMessages :: (ErrorMessage -> ErrorMessage) -> MultipleErrors -> MultipleErrors |
253 | 256 | onErrorMessages f = MultipleErrors . map f . runMultipleErrors |
254 | 257 |
|
255 | | -replaceUnknowns :: Type -> State [Unknown] Type |
| 258 | +-- | A map from rigid type variable name/unknown variable pairs to new variables. |
| 259 | +type UnknownMap = M.Map (Maybe String, Unknown) Unknown |
| 260 | + |
| 261 | +replaceUnknowns :: Type -> State UnknownMap Type |
256 | 262 | replaceUnknowns = everywhereOnTypesM replaceUnknowns' |
257 | 263 | where |
258 | | - lookupTable :: Unknown -> [Unknown] -> (Unknown, [Unknown]) |
259 | | - lookupTable x table = case (elemIndex x table) of |
260 | | - Nothing -> (length table, table ++ [x]) |
261 | | - Just i -> (i, table) |
262 | | - |
263 | | - replaceUnknowns' :: Type -> State [Unknown] Type |
264 | | - replaceUnknowns' (TUnknown u) = state $ first TUnknown . lookupTable u |
| 264 | + lookupTable :: (Maybe String, Unknown) -> UnknownMap -> (Unknown, UnknownMap) |
| 265 | + lookupTable x m = case M.lookup x m of |
| 266 | + Nothing -> let i = length (filter (on (==) fst x) (M.keys m)) in (i, M.insert x i m) |
| 267 | + Just i -> (i, m) |
| 268 | + |
| 269 | + replaceUnknowns' :: Type -> State UnknownMap Type |
| 270 | + replaceUnknowns' (TUnknown u) = state $ first TUnknown . lookupTable (Nothing, u) |
| 271 | + replaceUnknowns' (Skolem name s sko) = state $ first (flip (Skolem name) sko) . lookupTable (Just name, s) |
265 | 272 | replaceUnknowns' other = return other |
266 | 273 |
|
267 | | - |
268 | 274 | onTypesInErrorMessageM :: (Applicative m) => (Type -> m Type) -> ErrorMessage -> m ErrorMessage |
269 | 275 | onTypesInErrorMessageM f = g |
270 | 276 | where |
@@ -298,7 +304,7 @@ onTypesInErrorMessageM f = g |
298 | 304 | -- | |
299 | 305 | -- Pretty print a single error, simplifying if necessary |
300 | 306 | -- |
301 | | -prettyPrintSingleError :: Bool -> ErrorMessage -> State [Unknown] Box.Box |
| 307 | +prettyPrintSingleError :: Bool -> ErrorMessage -> State UnknownMap Box.Box |
302 | 308 | prettyPrintSingleError full e = prettyPrintErrorMessage <$> onTypesInErrorMessageM replaceUnknowns (if full then e else simplifyErrorMessage e) |
303 | 309 | where |
304 | 310 | -- | |
@@ -569,15 +575,15 @@ prettyPrintSingleError full e = prettyPrintErrorMessage <$> onTypesInErrorMessag |
569 | 575 | -- Pretty print multiple errors |
570 | 576 | -- |
571 | 577 | prettyPrintMultipleErrors :: Bool -> MultipleErrors -> String |
572 | | -prettyPrintMultipleErrors full = flip evalState [] . prettyPrintMultipleErrorsWith "Error:" "Multiple errors:" full |
| 578 | +prettyPrintMultipleErrors full = flip evalState M.empty . prettyPrintMultipleErrorsWith "Error:" "Multiple errors:" full |
573 | 579 |
|
574 | 580 | -- | |
575 | 581 | -- Pretty print multiple warnings |
576 | 582 | -- |
577 | 583 | prettyPrintMultipleWarnings :: Bool -> MultipleErrors -> String |
578 | | -prettyPrintMultipleWarnings full = flip evalState [] . prettyPrintMultipleErrorsWith "Warning:" "Multiple warnings:" full |
| 584 | +prettyPrintMultipleWarnings full = flip evalState M.empty . prettyPrintMultipleErrorsWith "Warning:" "Multiple warnings:" full |
579 | 585 |
|
580 | | -prettyPrintMultipleErrorsWith :: String -> String -> Bool -> MultipleErrors -> State [Unknown] String |
| 586 | +prettyPrintMultipleErrorsWith :: String -> String -> Bool -> MultipleErrors -> State UnknownMap String |
581 | 587 | prettyPrintMultipleErrorsWith intro _ full (MultipleErrors [e]) = do |
582 | 588 | result <- prettyPrintSingleError full e |
583 | 589 | return $ renderBox $ |
|
0 commit comments