{-# LANGUAGE ViewPatterns, ScopedTypeVariables #-}
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE TypeFamilies #-}
module Hint.Bracket(bracketHint) where
import Hint.Type(DeclHint,Idea(..),rawIdea,warn,suggest,Severity(..),toRefactSrcSpan,toSS)
import Data.Data
import Data.List.Extra
import Data.Generics.Uniplate.DataOnly
import Refact.Types
import GHC.Hs
import Outputable
import SrcLoc
import GHC.Util
import Language.Haskell.GhclibParserEx.GHC.Hs.Expr
import Language.Haskell.GhclibParserEx.GHC.Utils.Outputable
bracketHint :: DeclHint
bracketHint :: DeclHint
bracketHint Scope
_ ModuleEx
_ LHsDecl GhcPs
x =
(LHsExpr GhcPs -> [Idea]) -> [LHsExpr GhcPs] -> [Idea]
forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
concatMap (\LHsExpr GhcPs
x -> (LHsExpr GhcPs -> String)
-> (LHsExpr GhcPs -> Bool) -> Bool -> LHsExpr GhcPs -> [Idea]
forall a.
(Data a, Data (SrcSpanLess a), HasSrcSpan a, Outputable a,
Brackets a) =>
(a -> String) -> (a -> Bool) -> Bool -> a -> [Idea]
bracket LHsExpr GhcPs -> String
prettyExpr LHsExpr GhcPs -> Bool
isPartialAtom Bool
True LHsExpr GhcPs
x [Idea] -> [Idea] -> [Idea]
forall a. [a] -> [a] -> [a]
++ LHsExpr GhcPs -> [Idea]
dollar LHsExpr GhcPs
x) (LHsDecl GhcPs -> [LHsExpr GhcPs]
forall from to. Biplate from to => from -> [to]
childrenBi ((AnnDecl GhcPs -> AnnDecl GhcPs) -> LHsDecl GhcPs -> LHsDecl GhcPs
forall from to. Biplate from to => (to -> to) -> from -> from
descendBi AnnDecl GhcPs -> AnnDecl GhcPs
annotations LHsDecl GhcPs
x) :: [LHsExpr GhcPs]) [Idea] -> [Idea] -> [Idea]
forall a. [a] -> [a] -> [a]
++
(LHsType GhcPs -> [Idea]) -> [LHsType GhcPs] -> [Idea]
forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
concatMap ((LHsType GhcPs -> String)
-> (LHsType GhcPs -> Bool) -> Bool -> LHsType GhcPs -> [Idea]
forall a.
(Data a, Data (SrcSpanLess a), HasSrcSpan a, Outputable a,
Brackets a) =>
(a -> String) -> (a -> Bool) -> Bool -> a -> [Idea]
bracket LHsType GhcPs -> String
forall a. Outputable a => a -> String
unsafePrettyPrint (Bool -> LHsType GhcPs -> Bool
forall a b. a -> b -> a
const Bool
False) Bool
False) (LHsDecl GhcPs -> [LHsType GhcPs]
forall from to. Biplate from to => from -> [to]
childrenBi LHsDecl GhcPs
x :: [LHsType GhcPs]) [Idea] -> [Idea] -> [Idea]
forall a. [a] -> [a] -> [a]
++
(Located (Pat GhcPs) -> [Idea]) -> [Located (Pat GhcPs)] -> [Idea]
forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
concatMap ((Located (Pat GhcPs) -> String)
-> (Located (Pat GhcPs) -> Bool)
-> Bool
-> Located (Pat GhcPs)
-> [Idea]
forall a.
(Data a, Data (SrcSpanLess a), HasSrcSpan a, Outputable a,
Brackets a) =>
(a -> String) -> (a -> Bool) -> Bool -> a -> [Idea]
bracket Located (Pat GhcPs) -> String
forall a. Outputable a => a -> String
unsafePrettyPrint (Bool -> Located (Pat GhcPs) -> Bool
forall a b. a -> b -> a
const Bool
False) Bool
False) (LHsDecl GhcPs -> [Located (Pat GhcPs)]
forall from to. Biplate from to => from -> [to]
childrenBi LHsDecl GhcPs
x :: [LPat GhcPs]) [Idea] -> [Idea] -> [Idea]
forall a. [a] -> [a] -> [a]
++
(LConDeclField GhcPs -> [Idea]) -> [LConDeclField GhcPs] -> [Idea]
forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
concatMap LConDeclField GhcPs -> [Idea]
fieldDecl (LHsDecl GhcPs -> [LConDeclField GhcPs]
forall from to. Biplate from to => from -> [to]
childrenBi LHsDecl GhcPs
x)
where
annotations :: AnnDecl GhcPs -> AnnDecl GhcPs
annotations :: AnnDecl GhcPs -> AnnDecl GhcPs
annotations= (LHsExpr GhcPs -> LHsExpr GhcPs) -> AnnDecl GhcPs -> AnnDecl GhcPs
forall from to. Biplate from to => (to -> to) -> from -> from
descendBi ((LHsExpr GhcPs -> LHsExpr GhcPs)
-> AnnDecl GhcPs -> AnnDecl GhcPs)
-> (LHsExpr GhcPs -> LHsExpr GhcPs)
-> AnnDecl GhcPs
-> AnnDecl GhcPs
forall a b. (a -> b) -> a -> b
$ \LHsExpr GhcPs
x -> case (LHsExpr GhcPs
x :: LHsExpr GhcPs) of
L SrcSpan
l (HsPar XPar GhcPs
_ LHsExpr GhcPs
x) -> LHsExpr GhcPs
x
LHsExpr GhcPs
x -> LHsExpr GhcPs
x
prettyExpr :: LHsExpr GhcPs -> String
prettyExpr :: LHsExpr GhcPs -> String
prettyExpr s :: LHsExpr GhcPs
s@(L SrcSpan
_ SectionL{}) = LHsExpr GhcPs -> String
forall a. Outputable a => a -> String
unsafePrettyPrint (SrcSpanLess (LHsExpr GhcPs) -> LHsExpr GhcPs
forall a. HasSrcSpan a => SrcSpanLess a -> a
noLoc (XPar GhcPs -> LHsExpr GhcPs -> HsExpr GhcPs
forall p. XPar p -> LHsExpr p -> HsExpr p
HsPar NoExtField
XPar GhcPs
noExtField LHsExpr GhcPs
s) :: LHsExpr GhcPs)
prettyExpr s :: LHsExpr GhcPs
s@(L SrcSpan
_ SectionR{}) = LHsExpr GhcPs -> String
forall a. Outputable a => a -> String
unsafePrettyPrint (SrcSpanLess (LHsExpr GhcPs) -> LHsExpr GhcPs
forall a. HasSrcSpan a => SrcSpanLess a -> a
noLoc (XPar GhcPs -> LHsExpr GhcPs -> HsExpr GhcPs
forall p. XPar p -> LHsExpr p -> HsExpr p
HsPar NoExtField
XPar GhcPs
noExtField LHsExpr GhcPs
s) :: LHsExpr GhcPs)
prettyExpr LHsExpr GhcPs
x = LHsExpr GhcPs -> String
forall a. Outputable a => a -> String
unsafePrettyPrint LHsExpr GhcPs
x
tyConToRtype :: String -> RType
tyConToRtype :: String -> RType
tyConToRtype String
"Exp" = RType
Expr
tyConToRtype String
"Type" = RType
Type
tyConToRtype String
"HsType" = RType
Type
tyConToRtype String
"Pat" = RType
Pattern
tyConToRtype String
_ = RType
Expr
findType :: (Data a) => a -> RType
findType :: a -> RType
findType = String -> RType
tyConToRtype (String -> RType) -> (a -> String) -> a -> RType
forall b c a. (b -> c) -> (a -> b) -> a -> c
. DataType -> String
dataTypeName (DataType -> String) -> (a -> DataType) -> a -> String
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> DataType
forall a. Data a => a -> DataType
dataTypeOf
remParens' :: Brackets a => a -> Maybe a
remParens' :: a -> Maybe a
remParens' = (a -> a) -> Maybe a -> Maybe a
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap a -> a
forall a. Brackets a => a -> a
go (Maybe a -> Maybe a) -> (a -> Maybe a) -> a -> Maybe a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> Maybe a
forall a. Brackets a => a -> Maybe a
remParen
where
go :: a -> a
go a
e = a -> (a -> a) -> Maybe a -> a
forall b a. b -> (a -> b) -> Maybe a -> b
maybe a
e a -> a
go (a -> Maybe a
forall a. Brackets a => a -> Maybe a
remParen a
e)
isPartialAtom :: LHsExpr GhcPs -> Bool
isPartialAtom :: LHsExpr GhcPs -> Bool
isPartialAtom (L SrcSpan
_ (HsSpliceE XSpliceE GhcPs
_ (HsTypedSplice XTypedSplice GhcPs
_ SpliceDecoration
HasDollar IdP GhcPs
_ LHsExpr GhcPs
_) )) = Bool
True
isPartialAtom (L SrcSpan
_ (HsSpliceE XSpliceE GhcPs
_ (HsUntypedSplice XUntypedSplice GhcPs
_ SpliceDecoration
HasDollar IdP GhcPs
_ LHsExpr GhcPs
_) )) = Bool
True
isPartialAtom LHsExpr GhcPs
x = LHsExpr GhcPs -> Bool
isRecConstr LHsExpr GhcPs
x Bool -> Bool -> Bool
|| LHsExpr GhcPs -> Bool
isRecUpdate LHsExpr GhcPs
x
bracket :: forall a . (Data a, Data (SrcSpanLess a), HasSrcSpan a, Outputable a, Brackets a) => (a -> String) -> (a -> Bool) -> Bool -> a -> [Idea]
bracket :: (a -> String) -> (a -> Bool) -> Bool -> a -> [Idea]
bracket a -> String
pretty a -> Bool
isPartialAtom Bool
root = Maybe (Int, a, a -> a) -> a -> [Idea]
(HasSrcSpan a, Data a, Outputable a, Brackets a) =>
Maybe (Int, a, a -> a) -> a -> [Idea]
f Maybe (Int, a, a -> a)
forall a. Maybe a
Nothing
where
msg :: String
msg = String
"Redundant bracket"
f :: (HasSrcSpan a, Data a, Outputable a, Brackets a) => Maybe (Int, a , a -> a) -> a -> [Idea]
f :: Maybe (Int, a, a -> a) -> a -> [Idea]
f Maybe (Int, a, a -> a)
Nothing o :: a
o@(a -> Maybe a
forall a. Brackets a => a -> Maybe a
remParens' -> Just a
x)
| Bool
root Bool -> Bool -> Bool
|| a -> Bool
forall a. Brackets a => a -> Bool
isAtom a
x
, Bool -> Bool
not (Bool -> Bool) -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ a -> Bool
isPartialAtom a
x =
(if a -> Bool
forall a. Brackets a => a -> Bool
isAtom a
x then String -> a -> a -> Idea
forall a b.
(HasSrcSpan a, HasSrcSpan b, Data (SrcSpanLess b), Outputable a,
Outputable b) =>
String -> a -> b -> Idea
bracketError else String -> a -> a -> Idea
forall a b.
(HasSrcSpan a, HasSrcSpan b, Data (SrcSpanLess b), Outputable a,
Outputable b) =>
String -> a -> b -> Idea
bracketWarning) String
msg a
o a
x Idea -> [Idea] -> [Idea]
forall a. a -> [a] -> [a]
: a -> [Idea]
(HasSrcSpan a, Data a, Outputable a, Brackets a) => a -> [Idea]
g a
x
f Just{} o :: a
o@(a -> Maybe a
forall a. Brackets a => a -> Maybe a
remParens' -> Just a
x)
| a -> Bool
forall a. Brackets a => a -> Bool
isAtom a
x
, Bool -> Bool
not (Bool -> Bool) -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ a -> Bool
isPartialAtom a
x =
String -> a -> a -> Idea
forall a b.
(HasSrcSpan a, HasSrcSpan b, Data (SrcSpanLess b), Outputable a,
Outputable b) =>
String -> a -> b -> Idea
bracketError String
msg a
o a
x Idea -> [Idea] -> [Idea]
forall a. a -> [a] -> [a]
: a -> [Idea]
(HasSrcSpan a, Data a, Outputable a, Brackets a) => a -> [Idea]
g a
x
f (Just (Int
i, a
o, a -> a
gen)) v :: a
v@(a -> Maybe a
forall a. Brackets a => a -> Maybe a
remParens' -> Just a
x)
| Bool -> Bool
not (Bool -> Bool) -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ Int -> a -> a -> Bool
forall a. Brackets a => Int -> a -> a -> Bool
needBracket Int
i a
o a
x, Bool -> Bool
not (Bool -> Bool) -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ a -> Bool
isPartialAtom a
x =
Severity
-> String
-> SrcSpan
-> String
-> Maybe String
-> [Note]
-> [Refactoring SrcSpan]
-> Idea
rawIdea Severity
Suggestion String
msg (a -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
getLoc a
v) (a -> String
pretty a
o) (String -> Maybe String
forall a. a -> Maybe a
Just (a -> String
pretty (a -> a
gen a
x))) [] [Refactoring SrcSpan
r] Idea -> [Idea] -> [Idea]
forall a. a -> [a] -> [a]
: a -> [Idea]
(HasSrcSpan a, Data a, Outputable a, Brackets a) => a -> [Idea]
g a
x
where
typ :: RType
typ = SrcSpanLess a -> RType
forall a. Data a => a -> RType
findType (a -> SrcSpanLess a
forall a. HasSrcSpan a => a -> SrcSpanLess a
unLoc a
v)
r :: Refactoring SrcSpan
r = RType
-> SrcSpan -> [(String, SrcSpan)] -> String -> Refactoring SrcSpan
forall a. RType -> a -> [(String, a)] -> String -> Refactoring a
Replace RType
typ (a -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS a
v) [(String
"x", a -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS a
x)] String
"x"
f Maybe (Int, a, a -> a)
_ a
x = a -> [Idea]
(HasSrcSpan a, Data a, Outputable a, Brackets a) => a -> [Idea]
g a
x
g :: (HasSrcSpan a, Data a, Outputable a, Brackets a) => a -> [Idea]
g :: a -> [Idea]
g a
o = [[Idea]] -> [Idea]
forall (t :: * -> *) a. Foldable t => t [a] -> [a]
concat [Maybe (Int, a, a -> a) -> a -> [Idea]
(HasSrcSpan a, Data a, Outputable a, Brackets a) =>
Maybe (Int, a, a -> a) -> a -> [Idea]
f ((Int, a, a -> a) -> Maybe (Int, a, a -> a)
forall a. a -> Maybe a
Just (Int
i, a
o, a -> a
gen)) a
x | (Int
i, (a
x, a -> a
gen)) <- Int -> [(a, a -> a)] -> [(Int, (a, a -> a))]
forall a b. Enum a => a -> [b] -> [(a, b)]
zipFrom Int
0 ([(a, a -> a)] -> [(Int, (a, a -> a))])
-> [(a, a -> a)] -> [(Int, (a, a -> a))]
forall a b. (a -> b) -> a -> b
$ a -> [(a, a -> a)]
forall on. Uniplate on => on -> [(on, on -> on)]
holes a
o]
bracketWarning :: (HasSrcSpan a, HasSrcSpan b, Data (SrcSpanLess b), Outputable a, Outputable b) => String -> a -> b -> Idea
bracketWarning :: String -> a -> b -> Idea
bracketWarning String
msg a
o b
x =
String -> a -> b -> [Refactoring SrcSpan] -> Idea
forall a b.
(HasSrcSpan a, Outputable a, HasSrcSpan b, Outputable b) =>
String -> a -> b -> [Refactoring SrcSpan] -> Idea
suggest String
msg a
o b
x [RType
-> SrcSpan -> [(String, SrcSpan)] -> String -> Refactoring SrcSpan
forall a. RType -> a -> [(String, a)] -> String -> Refactoring a
Replace (SrcSpanLess b -> RType
forall a. Data a => a -> RType
findType (b -> SrcSpanLess b
forall a. HasSrcSpan a => a -> SrcSpanLess a
unLoc b
x)) (a -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS a
o) [(String
"x", b -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS b
x)] String
"x"]
bracketError :: (HasSrcSpan a, HasSrcSpan b, Data (SrcSpanLess b), Outputable a, Outputable b ) => String -> a -> b -> Idea
bracketError :: String -> a -> b -> Idea
bracketError String
msg a
o b
x =
String -> a -> b -> [Refactoring SrcSpan] -> Idea
forall a b.
(HasSrcSpan a, Outputable a, HasSrcSpan b, Outputable b) =>
String -> a -> b -> [Refactoring SrcSpan] -> Idea
warn String
msg a
o b
x [RType
-> SrcSpan -> [(String, SrcSpan)] -> String -> Refactoring SrcSpan
forall a. RType -> a -> [(String, a)] -> String -> Refactoring a
Replace (SrcSpanLess b -> RType
forall a. Data a => a -> RType
findType (b -> SrcSpanLess b
forall a. HasSrcSpan a => a -> SrcSpanLess a
unLoc b
x)) (a -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS a
o) [(String
"x", b -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS b
x)] String
"x"]
fieldDecl :: LConDeclField GhcPs -> [Idea]
fieldDecl :: LConDeclField GhcPs -> [Idea]
fieldDecl o :: LConDeclField GhcPs
o@(L SrcSpan
loc f :: ConDeclField GhcPs
f@ConDeclField{cd_fld_type :: forall pass. ConDeclField pass -> LBangType pass
cd_fld_type=v :: LHsType GhcPs
v@(L SrcSpan
l (HsParTy XParTy GhcPs
_ LHsType GhcPs
c))}) =
let r :: LConDeclField GhcPs
r = SrcSpan -> ConDeclField GhcPs -> LConDeclField GhcPs
forall l e. l -> e -> GenLocated l e
L SrcSpan
loc (ConDeclField GhcPs
f{cd_fld_type :: LHsType GhcPs
cd_fld_type=LHsType GhcPs
c}) :: LConDeclField GhcPs in
[Severity
-> String
-> SrcSpan
-> String
-> Maybe String
-> [Note]
-> [Refactoring SrcSpan]
-> Idea
rawIdea Severity
Suggestion String
"Redundant bracket" SrcSpan
l
(SDoc -> String
showSDocUnsafe (SDoc -> String) -> SDoc -> String
forall a b. (a -> b) -> a -> b
$ LConDeclField GhcPs -> SDoc
forall pass l.
(Outputable (XXConDeclField pass), Outputable (HsType pass)) =>
GenLocated l (ConDeclField pass) -> SDoc
ppr_fld LConDeclField GhcPs
o)
(String -> Maybe String
forall a. a -> Maybe a
Just (SDoc -> String
showSDocUnsafe (SDoc -> String) -> SDoc -> String
forall a b. (a -> b) -> a -> b
$ LConDeclField GhcPs -> SDoc
forall pass l.
(Outputable (XXConDeclField pass), Outputable (HsType pass)) =>
GenLocated l (ConDeclField pass) -> SDoc
ppr_fld LConDeclField GhcPs
r))
[]
[RType
-> SrcSpan -> [(String, SrcSpan)] -> String -> Refactoring SrcSpan
forall a. RType -> a -> [(String, a)] -> String -> Refactoring a
Replace RType
Type (LHsType GhcPs -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS LHsType GhcPs
v) [(String
"x", LHsType GhcPs -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS LHsType GhcPs
c)] String
"x"]]
where
ppr_fld :: GenLocated l (ConDeclField pass) -> SDoc
ppr_fld (L l
_ ConDeclField { cd_fld_names :: forall pass. ConDeclField pass -> [LFieldOcc pass]
cd_fld_names = [LFieldOcc pass]
ns, cd_fld_type :: forall pass. ConDeclField pass -> LBangType pass
cd_fld_type = LBangType pass
ty, cd_fld_doc :: forall pass. ConDeclField pass -> Maybe LHsDocString
cd_fld_doc = Maybe LHsDocString
doc })
= [LFieldOcc pass] -> SDoc
forall a. Outputable a => [a] -> SDoc
ppr_names [LFieldOcc pass]
ns SDoc -> SDoc -> SDoc
<+> SDoc
dcolon SDoc -> SDoc -> SDoc
<+> LBangType pass -> SDoc
forall a. Outputable a => a -> SDoc
ppr LBangType pass
ty SDoc -> SDoc -> SDoc
<+> Maybe LHsDocString -> SDoc
ppr_mbDoc Maybe LHsDocString
doc
ppr_fld (L l
_ (XConDeclField XXConDeclField pass
x)) = XXConDeclField pass -> SDoc
forall a. Outputable a => a -> SDoc
ppr XXConDeclField pass
x
ppr_names :: [a] -> SDoc
ppr_names [a
n] = a -> SDoc
forall a. Outputable a => a -> SDoc
ppr a
n
ppr_names [a]
ns = [SDoc] -> SDoc
sep (SDoc -> [SDoc] -> [SDoc]
punctuate SDoc
comma ((a -> SDoc) -> [a] -> [SDoc]
forall a b. (a -> b) -> [a] -> [b]
map a -> SDoc
forall a. Outputable a => a -> SDoc
ppr [a]
ns))
fieldDecl LConDeclField GhcPs
_ = []
dollar :: LHsExpr GhcPs -> [Idea]
dollar :: LHsExpr GhcPs -> [Idea]
dollar = (LHsExpr GhcPs -> [Idea]) -> [LHsExpr GhcPs] -> [Idea]
forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
concatMap LHsExpr GhcPs -> [Idea]
f ([LHsExpr GhcPs] -> [Idea])
-> (LHsExpr GhcPs -> [LHsExpr GhcPs]) -> LHsExpr GhcPs -> [Idea]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. LHsExpr GhcPs -> [LHsExpr GhcPs]
forall on. Uniplate on => on -> [on]
universe
where
f :: LHsExpr GhcPs -> [Idea]
f LHsExpr GhcPs
x = [ (String
-> LHsExpr GhcPs -> LHsExpr GhcPs -> [Refactoring SrcSpan] -> Idea
forall a b.
(HasSrcSpan a, Outputable a, HasSrcSpan b, Outputable b) =>
String -> a -> b -> [Refactoring SrcSpan] -> Idea
suggest String
"Redundant $" LHsExpr GhcPs
x LHsExpr GhcPs
y [Refactoring SrcSpan
r]){ideaSpan :: SrcSpan
ideaSpan = LHsExpr GhcPs -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
getLoc LHsExpr GhcPs
d} | o :: LHsExpr GhcPs
o@(L SrcSpan
_ (OpApp XOpApp GhcPs
_ LHsExpr GhcPs
a LHsExpr GhcPs
d LHsExpr GhcPs
b)) <- [LHsExpr GhcPs
x], LHsExpr GhcPs -> Bool
isDol LHsExpr GhcPs
d
, let y :: LHsExpr GhcPs
y = SrcSpanLess (LHsExpr GhcPs) -> LHsExpr GhcPs
forall a. HasSrcSpan a => SrcSpanLess a -> a
noLoc (XApp GhcPs -> LHsExpr GhcPs -> LHsExpr GhcPs -> HsExpr GhcPs
forall p. XApp p -> LHsExpr p -> LHsExpr p -> HsExpr p
HsApp NoExtField
XApp GhcPs
noExtField LHsExpr GhcPs
a LHsExpr GhcPs
b) :: LHsExpr GhcPs
, Bool -> Bool
not (Bool -> Bool) -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ Int -> LHsExpr GhcPs -> LHsExpr GhcPs -> Bool
forall a. Brackets a => Int -> a -> a -> Bool
needBracket Int
0 LHsExpr GhcPs
y LHsExpr GhcPs
a
, Bool -> Bool
not (Bool -> Bool) -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ Int -> LHsExpr GhcPs -> LHsExpr GhcPs -> Bool
forall a. Brackets a => Int -> a -> a -> Bool
needBracket Int
1 LHsExpr GhcPs
y LHsExpr GhcPs
b
, Bool -> Bool
not (Bool -> Bool) -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ LHsExpr GhcPs -> Bool
isPartialAtom LHsExpr GhcPs
b
, let r :: Refactoring SrcSpan
r = RType
-> SrcSpan -> [(String, SrcSpan)] -> String -> Refactoring SrcSpan
forall a. RType -> a -> [(String, a)] -> String -> Refactoring a
Replace RType
Expr (LHsExpr GhcPs -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS LHsExpr GhcPs
x) [(String
"a", LHsExpr GhcPs -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS LHsExpr GhcPs
a), (String
"b", LHsExpr GhcPs -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS LHsExpr GhcPs
b)] String
"a b"]
[Idea] -> [Idea] -> [Idea]
forall a. [a] -> [a] -> [a]
++
[ String
-> LHsExpr GhcPs -> LHsExpr GhcPs -> [Refactoring SrcSpan] -> Idea
forall a b.
(HasSrcSpan a, Outputable a, HasSrcSpan b, Outputable b) =>
String -> a -> b -> [Refactoring SrcSpan] -> Idea
suggest String
"Move brackets to avoid $" LHsExpr GhcPs
x (LHsExpr GhcPs -> LHsExpr GhcPs
t LHsExpr GhcPs
y) [Refactoring SrcSpan
r]
|(LHsExpr GhcPs -> LHsExpr GhcPs
t, e :: LHsExpr GhcPs
e@(L SrcSpan
_ (HsPar XPar GhcPs
_ (L SrcSpan
_ (OpApp XOpApp GhcPs
_ LHsExpr GhcPs
a1 LHsExpr GhcPs
op1 LHsExpr GhcPs
a2))))) <- LHsExpr GhcPs -> [(LHsExpr GhcPs -> LHsExpr GhcPs, LHsExpr GhcPs)]
splitInfix LHsExpr GhcPs
x
, LHsExpr GhcPs -> Bool
isDol LHsExpr GhcPs
op1
, LHsExpr GhcPs -> Bool
isVar LHsExpr GhcPs
a1 Bool -> Bool -> Bool
|| LHsExpr GhcPs -> Bool
isApp LHsExpr GhcPs
a1 Bool -> Bool -> Bool
|| LHsExpr GhcPs -> Bool
isPar LHsExpr GhcPs
a1, Bool -> Bool
not (Bool -> Bool) -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ LHsExpr GhcPs -> Bool
forall a. Brackets a => a -> Bool
isAtom LHsExpr GhcPs
a2
, LHsExpr GhcPs -> String
varToStr LHsExpr GhcPs
a1 String -> String -> Bool
forall a. Eq a => a -> a -> Bool
/= String
"select"
, let y :: LHsExpr GhcPs
y = SrcSpanLess (LHsExpr GhcPs) -> LHsExpr GhcPs
forall a. HasSrcSpan a => SrcSpanLess a -> a
noLoc (SrcSpanLess (LHsExpr GhcPs) -> LHsExpr GhcPs)
-> SrcSpanLess (LHsExpr GhcPs) -> LHsExpr GhcPs
forall a b. (a -> b) -> a -> b
$ XApp GhcPs -> LHsExpr GhcPs -> LHsExpr GhcPs -> HsExpr GhcPs
forall p. XApp p -> LHsExpr p -> LHsExpr p -> HsExpr p
HsApp NoExtField
XApp GhcPs
noExtField LHsExpr GhcPs
a1 (SrcSpanLess (LHsExpr GhcPs) -> LHsExpr GhcPs
forall a. HasSrcSpan a => SrcSpanLess a -> a
noLoc (XPar GhcPs -> LHsExpr GhcPs -> HsExpr GhcPs
forall p. XPar p -> LHsExpr p -> HsExpr p
HsPar NoExtField
XPar GhcPs
noExtField LHsExpr GhcPs
a2))
, let r :: Refactoring SrcSpan
r = RType
-> SrcSpan -> [(String, SrcSpan)] -> String -> Refactoring SrcSpan
forall a. RType -> a -> [(String, a)] -> String -> Refactoring a
Replace RType
Expr (LHsExpr GhcPs -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS LHsExpr GhcPs
e) [(String
"a", LHsExpr GhcPs -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS LHsExpr GhcPs
a1), (String
"b", LHsExpr GhcPs -> SrcSpan
forall a. HasSrcSpan a => a -> SrcSpan
toSS LHsExpr GhcPs
a2)] String
"a (b)" ]
[Idea] -> [Idea] -> [Idea]
forall a. [a] -> [a] -> [a]
++
[ (String
-> LHsExpr GhcPs -> LHsExpr GhcPs -> [Refactoring SrcSpan] -> Idea
forall a b.
(HasSrcSpan a, Outputable a, HasSrcSpan b, Outputable b) =>
String -> a -> b -> [Refactoring SrcSpan] -> Idea
suggest String
"Redundant bracket" LHsExpr GhcPs
x LHsExpr GhcPs
y [Refactoring SrcSpan
r]){ideaSpan :: SrcSpan
ideaSpan = SrcSpan
locPar}
| L SrcSpan
_ (OpApp XOpApp GhcPs
_ (L SrcSpan
locPar (HsPar XPar GhcPs
_ o1 :: LHsExpr GhcPs
o1@(L SrcSpan
locNoPar (OpApp XOpApp GhcPs
_ LHsExpr GhcPs
v1 (LHsExpr GhcPs -> Bool
isDot -> Bool
True) LHsExpr GhcPs
v2)))) LHsExpr GhcPs
o2 LHsExpr GhcPs
v3) <- [LHsExpr GhcPs
x], LHsExpr GhcPs -> String
varToStr LHsExpr GhcPs
o2 String -> String -> Bool
forall a. Eq a => a -> a -> Bool
== String
"<$>"
, let y :: LHsExpr GhcPs
y = SrcSpanLess (LHsExpr GhcPs) -> LHsExpr GhcPs
forall a. HasSrcSpan a => SrcSpanLess a -> a
noLoc (XOpApp GhcPs
-> LHsExpr GhcPs -> LHsExpr GhcPs -> LHsExpr GhcPs -> HsExpr GhcPs
forall p.
XOpApp p -> LHsExpr p -> LHsExpr p -> LHsExpr p -> HsExpr p
OpApp NoExtField
XOpApp GhcPs
noExtField LHsExpr GhcPs
o1 LHsExpr GhcPs
o2 LHsExpr GhcPs
v3) :: LHsExpr GhcPs
, let r :: Refactoring SrcSpan
r = RType
-> SrcSpan -> [(String, SrcSpan)] -> String -> Refactoring SrcSpan
forall a. RType -> a -> [(String, a)] -> String -> Refactoring a
Replace RType
Expr (SrcSpan -> SrcSpan
toRefactSrcSpan SrcSpan
locPar) [(String
"a", SrcSpan -> SrcSpan
toRefactSrcSpan SrcSpan
locNoPar)] String
"a"]
[Idea] -> [Idea] -> [Idea]
forall a. [a] -> [a] -> [a]
++
[ String
-> LHsExpr GhcPs -> LHsExpr GhcPs -> [Refactoring SrcSpan] -> Idea
forall a b.
(HasSrcSpan a, Outputable a, HasSrcSpan b, Outputable b) =>
String -> a -> b -> [Refactoring SrcSpan] -> Idea
suggest String
"Redundant section" LHsExpr GhcPs
x LHsExpr GhcPs
y []
| L SrcSpan
_ (HsApp XApp GhcPs
_ (L SrcSpan
_ (HsPar XPar GhcPs
_ (L SrcSpan
_ (SectionL XSectionL GhcPs
_ LHsExpr GhcPs
a LHsExpr GhcPs
b)))) LHsExpr GhcPs
c) <- [LHsExpr GhcPs
x]
, let y :: LHsExpr GhcPs
y = SrcSpanLess (LHsExpr GhcPs) -> LHsExpr GhcPs
forall a. HasSrcSpan a => SrcSpanLess a -> a
noLoc (SrcSpanLess (LHsExpr GhcPs) -> LHsExpr GhcPs)
-> SrcSpanLess (LHsExpr GhcPs) -> LHsExpr GhcPs
forall a b. (a -> b) -> a -> b
$ XOpApp GhcPs
-> LHsExpr GhcPs -> LHsExpr GhcPs -> LHsExpr GhcPs -> HsExpr GhcPs
forall p.
XOpApp p -> LHsExpr p -> LHsExpr p -> LHsExpr p -> HsExpr p
OpApp NoExtField
XOpApp GhcPs
noExtField LHsExpr GhcPs
a LHsExpr GhcPs
b LHsExpr GhcPs
c :: LHsExpr GhcPs]
splitInfix :: LHsExpr GhcPs -> [(LHsExpr GhcPs -> LHsExpr GhcPs, LHsExpr GhcPs)]
splitInfix :: LHsExpr GhcPs -> [(LHsExpr GhcPs -> LHsExpr GhcPs, LHsExpr GhcPs)]
splitInfix (L SrcSpan
l (OpApp XOpApp GhcPs
_ LHsExpr GhcPs
lhs LHsExpr GhcPs
op LHsExpr GhcPs
rhs)) =
[(SrcSpan -> HsExpr GhcPs -> LHsExpr GhcPs
forall l e. l -> e -> GenLocated l e
L SrcSpan
l (HsExpr GhcPs -> LHsExpr GhcPs)
-> (LHsExpr GhcPs -> HsExpr GhcPs)
-> LHsExpr GhcPs
-> LHsExpr GhcPs
forall b c a. (b -> c) -> (a -> b) -> a -> c
. XOpApp GhcPs
-> LHsExpr GhcPs -> LHsExpr GhcPs -> LHsExpr GhcPs -> HsExpr GhcPs
forall p.
XOpApp p -> LHsExpr p -> LHsExpr p -> LHsExpr p -> HsExpr p
OpApp NoExtField
XOpApp GhcPs
noExtField LHsExpr GhcPs
lhs LHsExpr GhcPs
op, LHsExpr GhcPs
rhs), (\LHsExpr GhcPs
lhs -> SrcSpan -> HsExpr GhcPs -> LHsExpr GhcPs
forall l e. l -> e -> GenLocated l e
L SrcSpan
l (XOpApp GhcPs
-> LHsExpr GhcPs -> LHsExpr GhcPs -> LHsExpr GhcPs -> HsExpr GhcPs
forall p.
XOpApp p -> LHsExpr p -> LHsExpr p -> LHsExpr p -> HsExpr p
OpApp NoExtField
XOpApp GhcPs
noExtField LHsExpr GhcPs
lhs LHsExpr GhcPs
op LHsExpr GhcPs
rhs), LHsExpr GhcPs
lhs)]
splitInfix LHsExpr GhcPs
_ = []