on 53285db help sign in
ormolu/src/Ormolu/Diff.hs
61 lines 1.7 kB history raw
1{-# LANGUAGE DeriveDataTypeable #-}
2{-# LANGUAGE RankNTypes #-}
3{-# LANGUAGE RecordWildCards #-}
5-- | Diffing GHC ASTs modulo span positions.
7module Ormolu.Diff
8 ( diff
9 )
10where
12import Data.Generics
13import Data.Maybe (mapMaybe)
14import GHC
15import Language.Haskell.GHC.ExactPrint.Types
16import Ormolu.Comments
17import qualified Data.Map.Strict as M
19-- | Return 'False' of two annotated ASTs are the same modulo span
20-- positions.
22diff
23 :: (Anns, ParsedSource) -- ^ First annotated AST
24 -> (Anns, ParsedSource) -- ^ Second annotated AST
25 -> Bool
26diff (anns0, ps0) (anns1, ps1) =
27 not (matchIgnoringSrcSpans (simplifyAnns anns0) (simplifyAnns anns1))
28 || not (matchIgnoringSrcSpans ps0 ps1)
30-- | Compare two 'ParsedSource' values disregarding differences in
31-- 'SrcSpan's.
33matchIgnoringSrcSpans :: Data a => a -> a -> Bool
34matchIgnoringSrcSpans x0 y0 = geq' x0 y0
35 where
36 geq' :: GenericQ (GenericQ Bool)
37 geq' x y = (toConstr x == toConstr y)
38 && and (gzipWithQ (geq' `extQ` srcSpanEq) x y)
39 srcSpanEq :: SrcSpan -> GenericQ Bool
40 srcSpanEq _ _ = True
42-- | Simplified collection of 'Comment's.
44data Comments = Comments [Comment] [Comment] [Comment]
45 deriving (Show, Typeable, Data)
47-- | Simplify a collection of annotations.
49simplifyAnns :: Anns -> [Comments]
50simplifyAnns = fmap simplifyAnn . M.elems
52-- | Simplify single annotation.
54simplifyAnn :: Annotation -> Comments
55simplifyAnn Ann {..} = Comments
56 (f . fst <$> annPriorComments)
57 (f . fst <$> annFollowingComments)
58 (mapMaybe (fmap f . annComment) (fst <$> annsDP))
59 where
60 f (Comment str i o) =
61 Comment (unlines $ normalizeComment str) i o