module Seminal.Enumerator.LocalBindings (
    enumerateChangesInLocalBinds
) where
import Seminal.Enumerator.Enumerator (Enumerator)
import Seminal.Compiler.API
import Seminal.Change
    ( node,
      ChangeType(Removal),
      Change(Change),
      (<&&>)
    )
import Data.Functor ((<&>))
import Data.List.HT (splitEverywhere)
import Seminal.Enumerator.Signatures (enumerateChangeInSignature)
import {-# SOURCE #-} Seminal.Enumerator.Expressions (enumerateChangesInExpression)
import Seminal.Enumerator.Bindings (enumerateChangesInBinding)

-- | Enumeration of changes for local bindings, e.g. in a `let` or `where` clause
-- See [API doc](https://hackage.haskell.org/package/ghc-9.6.1/docs/Language-Haskell-Syntax-Binds.html#t:HsLocalBindsLR)
enumerateChangesInLocalBinds :: Enumerator (HsLocalBinds GhcPs)
enumerateChangesInLocalBinds :: Enumerator (HsLocalBinds GhcPs)
enumerateChangesInLocalBinds (HsValBinds XHsValBinds GhcPs GhcPs
ext HsValBindsLR GhcPs GhcPs
valbind) SrcSpan
_ = case HsValBindsLR GhcPs GhcPs
valbind of
    XValBindsLR {} -> []
    (ValBinds XValBinds GhcPs GhcPs
xbind LHsBindsLR GhcPs GhcPs
binds [LSig GhcPs]
signatures) -> [Change (HsLocalBinds GhcPs)]
enumSignatures [Change (HsLocalBinds GhcPs)]
-> [Change (HsLocalBinds GhcPs)] -> [Change (HsLocalBinds GhcPs)]
forall a. [a] -> [a] -> [a]
++ [Change (HsLocalBinds GhcPs)]
enumBinds
        where
            enumBinds :: [Change (HsLocalBinds GhcPs)]
enumBinds = [[Change (HsLocalBinds GhcPs)]] -> [Change (HsLocalBinds GhcPs)]
forall (t :: * -> *) a. Foldable t => t [a] -> [a]
concat ([[Change (HsLocalBinds GhcPs)]] -> [Change (HsLocalBinds GhcPs)])
-> [[Change (HsLocalBinds GhcPs)]] -> [Change (HsLocalBinds GhcPs)]
forall a b. (a -> b) -> a -> b
$ [GenLocated SrcSpanAnnA (HsBind GhcPs)]
-> [([GenLocated SrcSpanAnnA (HsBind GhcPs)],
     GenLocated SrcSpanAnnA (HsBind GhcPs),
     [GenLocated SrcSpanAnnA (HsBind GhcPs)])]
forall a. [a] -> [([a], a, [a])]
splitEverywhere (Bag (GenLocated SrcSpanAnnA (HsBind GhcPs))
-> [GenLocated SrcSpanAnnA (HsBind GhcPs)]
forall a. Bag a -> [a]
bagToList LHsBindsLR GhcPs GhcPs
Bag (GenLocated SrcSpanAnnA (HsBind GhcPs))
binds)
                [([GenLocated SrcSpanAnnA (HsBind GhcPs)],
  GenLocated SrcSpanAnnA (HsBind GhcPs),
  [GenLocated SrcSpanAnnA (HsBind GhcPs)])]
-> (([GenLocated SrcSpanAnnA (HsBind GhcPs)],
     GenLocated SrcSpanAnnA (HsBind GhcPs),
     [GenLocated SrcSpanAnnA (HsBind GhcPs)])
    -> [Change (HsLocalBinds GhcPs)])
-> [[Change (HsLocalBinds GhcPs)]]
forall (f :: * -> *) a b. Functor f => f a -> (a -> b) -> f b
<&> (\([GenLocated SrcSpanAnnA (HsBind GhcPs)]
h, L SrcSpanAnnA
lbind HsBind GhcPs
bind, [GenLocated SrcSpanAnnA (HsBind GhcPs)]
t) -> Enumerator (HsBind GhcPs)
enumerateChangesInBinding HsBind GhcPs
bind (SrcSpanAnnA -> SrcSpan
forall a. SrcSpanAnn' a -> SrcSpan
locA SrcSpanAnnA
lbind)
                        [Change (HsBind GhcPs)]
-> (HsBind GhcPs -> GenLocated SrcSpanAnnA (HsBind GhcPs))
-> [Change (GenLocated SrcSpanAnnA (HsBind GhcPs))]
forall a b. [Change a] -> (a -> b) -> [Change b]
<&&> (SrcSpanAnnA
-> HsBind GhcPs -> GenLocated SrcSpanAnnA (HsBind GhcPs)
forall l e. l -> e -> GenLocated l e
L SrcSpanAnnA
lbind)
                        [Change (GenLocated SrcSpanAnnA (HsBind GhcPs))]
-> (GenLocated SrcSpanAnnA (HsBind GhcPs)
    -> Bag (GenLocated SrcSpanAnnA (HsBind GhcPs)))
-> [Change (Bag (GenLocated SrcSpanAnnA (HsBind GhcPs)))]
forall a b. [Change a] -> (a -> b) -> [Change b]
<&&> (\GenLocated SrcSpanAnnA (HsBind GhcPs)
r ->  [GenLocated SrcSpanAnnA (HsBind GhcPs)]
-> Bag (GenLocated SrcSpanAnnA (HsBind GhcPs))
forall a. [a] -> Bag a
listToBag ([GenLocated SrcSpanAnnA (HsBind GhcPs)]
 -> Bag (GenLocated SrcSpanAnnA (HsBind GhcPs)))
-> [GenLocated SrcSpanAnnA (HsBind GhcPs)]
-> Bag (GenLocated SrcSpanAnnA (HsBind GhcPs))
forall a b. (a -> b) -> a -> b
$ [GenLocated SrcSpanAnnA (HsBind GhcPs)]
h [GenLocated SrcSpanAnnA (HsBind GhcPs)]
-> [GenLocated SrcSpanAnnA (HsBind GhcPs)]
-> [GenLocated SrcSpanAnnA (HsBind GhcPs)]
forall a. [a] -> [a] -> [a]
++ [GenLocated SrcSpanAnnA (HsBind GhcPs)
r] [GenLocated SrcSpanAnnA (HsBind GhcPs)]
-> [GenLocated SrcSpanAnnA (HsBind GhcPs)]
-> [GenLocated SrcSpanAnnA (HsBind GhcPs)]
forall a. [a] -> [a] -> [a]
++ [GenLocated SrcSpanAnnA (HsBind GhcPs)]
t)
                        [Change (Bag (GenLocated SrcSpanAnnA (HsBind GhcPs)))]
-> (Bag (GenLocated SrcSpanAnnA (HsBind GhcPs))
    -> HsValBindsLR GhcPs GhcPs)
-> [Change (HsValBindsLR GhcPs GhcPs)]
forall a b. [Change a] -> (a -> b) -> [Change b]
<&&> (\Bag (GenLocated SrcSpanAnnA (HsBind GhcPs))
b -> XValBinds GhcPs GhcPs
-> LHsBindsLR GhcPs GhcPs
-> [LSig GhcPs]
-> HsValBindsLR GhcPs GhcPs
forall idL idR.
XValBinds idL idR
-> LHsBindsLR idL idR -> [LSig idR] -> HsValBindsLR idL idR
ValBinds XValBinds GhcPs GhcPs
xbind LHsBindsLR GhcPs GhcPs
Bag (GenLocated SrcSpanAnnA (HsBind GhcPs))
b [LSig GhcPs]
signatures)
                        [Change (HsValBindsLR GhcPs GhcPs)]
-> (HsValBindsLR GhcPs GhcPs -> HsLocalBinds GhcPs)
-> [Change (HsLocalBinds GhcPs)]
forall a b. [Change a] -> (a -> b) -> [Change b]
<&&> (XHsValBinds GhcPs GhcPs
-> HsValBindsLR GhcPs GhcPs -> HsLocalBinds GhcPs
forall idL idR.
XHsValBinds idL idR
-> HsValBindsLR idL idR -> HsLocalBindsLR idL idR
HsValBinds XHsValBinds GhcPs GhcPs
ext)
                )
            enumSignatures :: [Change (HsLocalBinds GhcPs)]
enumSignatures = [[Change (HsLocalBinds GhcPs)]] -> [Change (HsLocalBinds GhcPs)]
forall (t :: * -> *) a. Foldable t => t [a] -> [a]
concat ([[Change (HsLocalBinds GhcPs)]] -> [Change (HsLocalBinds GhcPs)])
-> [[Change (HsLocalBinds GhcPs)]] -> [Change (HsLocalBinds GhcPs)]
forall a b. (a -> b) -> a -> b
$ [GenLocated SrcSpanAnnA (Sig GhcPs)]
-> [([GenLocated SrcSpanAnnA (Sig GhcPs)],
     GenLocated SrcSpanAnnA (Sig GhcPs),
     [GenLocated SrcSpanAnnA (Sig GhcPs)])]
forall a. [a] -> [([a], a, [a])]
splitEverywhere [LSig GhcPs]
[GenLocated SrcSpanAnnA (Sig GhcPs)]
signatures
                [([GenLocated SrcSpanAnnA (Sig GhcPs)],
  GenLocated SrcSpanAnnA (Sig GhcPs),
  [GenLocated SrcSpanAnnA (Sig GhcPs)])]
-> (([GenLocated SrcSpanAnnA (Sig GhcPs)],
     GenLocated SrcSpanAnnA (Sig GhcPs),
     [GenLocated SrcSpanAnnA (Sig GhcPs)])
    -> [Change (HsLocalBinds GhcPs)])
-> [[Change (HsLocalBinds GhcPs)]]
forall (f :: * -> *) a b. Functor f => f a -> (a -> b) -> f b
<&> (\([GenLocated SrcSpanAnnA (Sig GhcPs)]
h, L SrcSpanAnnA
lsig Sig GhcPs
sign, [GenLocated SrcSpanAnnA (Sig GhcPs)]
t) -> Enumerator (Sig GhcPs)
enumerateChangeInSignature Sig GhcPs
sign (SrcSpanAnnA -> SrcSpan
forall a. SrcSpanAnn' a -> SrcSpan
locA SrcSpanAnnA
lsig)
                        [Change (Sig GhcPs)]
-> (Sig GhcPs -> GenLocated SrcSpanAnnA (Sig GhcPs))
-> [Change (GenLocated SrcSpanAnnA (Sig GhcPs))]
forall a b. [Change a] -> (a -> b) -> [Change b]
<&&> (SrcSpanAnnA -> Sig GhcPs -> GenLocated SrcSpanAnnA (Sig GhcPs)
forall l e. l -> e -> GenLocated l e
L SrcSpanAnnA
lsig)
                        [Change (GenLocated SrcSpanAnnA (Sig GhcPs))]
-> (GenLocated SrcSpanAnnA (Sig GhcPs)
    -> [GenLocated SrcSpanAnnA (Sig GhcPs)])
-> [Change [GenLocated SrcSpanAnnA (Sig GhcPs)]]
forall a b. [Change a] -> (a -> b) -> [Change b]
<&&> (\GenLocated SrcSpanAnnA (Sig GhcPs)
r ->  [GenLocated SrcSpanAnnA (Sig GhcPs)]
h [GenLocated SrcSpanAnnA (Sig GhcPs)]
-> [GenLocated SrcSpanAnnA (Sig GhcPs)]
-> [GenLocated SrcSpanAnnA (Sig GhcPs)]
forall a. [a] -> [a] -> [a]
++ [GenLocated SrcSpanAnnA (Sig GhcPs)
r] [GenLocated SrcSpanAnnA (Sig GhcPs)]
-> [GenLocated SrcSpanAnnA (Sig GhcPs)]
-> [GenLocated SrcSpanAnnA (Sig GhcPs)]
forall a. [a] -> [a] -> [a]
++ [GenLocated SrcSpanAnnA (Sig GhcPs)]
t)
                        [Change [GenLocated SrcSpanAnnA (Sig GhcPs)]]
-> ([GenLocated SrcSpanAnnA (Sig GhcPs)] -> HsLocalBinds GhcPs)
-> [Change (HsLocalBinds GhcPs)]
forall a b. [Change a] -> (a -> b) -> [Change b]
<&&> (XHsValBinds GhcPs GhcPs
-> HsValBindsLR GhcPs GhcPs -> HsLocalBinds GhcPs
forall idL idR.
XHsValBinds idL idR
-> HsValBindsLR idL idR -> HsLocalBindsLR idL idR
HsValBinds XHsValBinds GhcPs GhcPs
ext (HsValBindsLR GhcPs GhcPs -> HsLocalBinds GhcPs)
-> ([GenLocated SrcSpanAnnA (Sig GhcPs)]
    -> HsValBindsLR GhcPs GhcPs)
-> [GenLocated SrcSpanAnnA (Sig GhcPs)]
-> HsLocalBinds GhcPs
forall b c a. (b -> c) -> (a -> b) -> a -> c
. XValBinds GhcPs GhcPs
-> LHsBindsLR GhcPs GhcPs
-> [LSig GhcPs]
-> HsValBindsLR GhcPs GhcPs
forall idL idR.
XValBinds idL idR
-> LHsBindsLR idL idR -> [LSig idR] -> HsValBindsLR idL idR
ValBinds XValBinds GhcPs GhcPs
xbind LHsBindsLR GhcPs GhcPs
binds)
                )
enumerateChangesInLocalBinds (HsIPBinds XHsIPBinds GhcPs GhcPs
ext HsIPBinds GhcPs
implicitbind) SrcSpan
l = case HsIPBinds GhcPs
implicitbind of
    IPBinds XIPBinds GhcPs
xbind [LIPBind GhcPs]
bindlist -> ([GenLocated SrcSpanAnnA (IPBind GhcPs)]
-> [([GenLocated SrcSpanAnnA (IPBind GhcPs)],
     GenLocated SrcSpanAnnA (IPBind GhcPs),
     [GenLocated SrcSpanAnnA (IPBind GhcPs)])]
forall a. [a] -> [([a], a, [a])]
splitEverywhere [LIPBind GhcPs]
[GenLocated SrcSpanAnnA (IPBind GhcPs)]
bindlist
        [([GenLocated SrcSpanAnnA (IPBind GhcPs)],
  GenLocated SrcSpanAnnA (IPBind GhcPs),
  [GenLocated SrcSpanAnnA (IPBind GhcPs)])]
-> (([GenLocated SrcSpanAnnA (IPBind GhcPs)],
     GenLocated SrcSpanAnnA (IPBind GhcPs),
     [GenLocated SrcSpanAnnA (IPBind GhcPs)])
    -> Change [GenLocated SrcSpanAnnA (IPBind GhcPs)])
-> [Change [GenLocated SrcSpanAnnA (IPBind GhcPs)]]
forall (f :: * -> *) a b. Functor f => f a -> (a -> b) -> f b
<&> (\([GenLocated SrcSpanAnnA (IPBind GhcPs)]
h, L SrcSpanAnnA
lbind IPBind GhcPs
bind, [GenLocated SrcSpanAnnA (IPBind GhcPs)]
t) -> ChangeNode [GenLocated SrcSpanAnnA (IPBind GhcPs)]
-> [ChangeNode [GenLocated SrcSpanAnnA (IPBind GhcPs)]]
-> SrcSpan
-> [Change [GenLocated SrcSpanAnnA (IPBind GhcPs)]]
-> String
-> ChangeType
-> Change [GenLocated SrcSpanAnnA (IPBind GhcPs)]
forall node.
ChangeNode node
-> [ChangeNode node]
-> SrcSpan
-> [Change node]
-> String
-> ChangeType
-> Change node
Change
            ([GenLocated SrcSpanAnnA (IPBind GhcPs)]
-> ChangeNode [GenLocated SrcSpanAnnA (IPBind GhcPs)]
forall n. Outputable n => n -> ChangeNode n
node [LIPBind GhcPs]
[GenLocated SrcSpanAnnA (IPBind GhcPs)]
bindlist)
            [[GenLocated SrcSpanAnnA (IPBind GhcPs)]
-> ChangeNode [GenLocated SrcSpanAnnA (IPBind GhcPs)]
forall n. Outputable n => n -> ChangeNode n
node ([GenLocated SrcSpanAnnA (IPBind GhcPs)]
 -> ChangeNode [GenLocated SrcSpanAnnA (IPBind GhcPs)])
-> [GenLocated SrcSpanAnnA (IPBind GhcPs)]
-> ChangeNode [GenLocated SrcSpanAnnA (IPBind GhcPs)]
forall a b. (a -> b) -> a -> b
$ [GenLocated SrcSpanAnnA (IPBind GhcPs)]
h [GenLocated SrcSpanAnnA (IPBind GhcPs)]
-> [GenLocated SrcSpanAnnA (IPBind GhcPs)]
-> [GenLocated SrcSpanAnnA (IPBind GhcPs)]
forall a. [a] -> [a] -> [a]
++ [GenLocated SrcSpanAnnA (IPBind GhcPs)]
t] -- Remove bind
            SrcSpan
l
            (case IPBind GhcPs
bind of
                IPBind XCIPBind GhcPs
bext XRec GhcPs HsIPName
lname (L SrcSpanAnnA
lexpr HsExpr GhcPs
expr) ->
                    Enumerator (HsExpr GhcPs)
enumerateChangesInExpression HsExpr GhcPs
expr (SrcSpanAnnA -> SrcSpan
forall a. SrcSpanAnn' a -> SrcSpan
locA SrcSpanAnnA
lexpr)
                    [Change (HsExpr GhcPs)]
-> (HsExpr GhcPs -> GenLocated SrcSpanAnnA (HsExpr GhcPs))
-> [Change (GenLocated SrcSpanAnnA (HsExpr GhcPs))]
forall a b. [Change a] -> (a -> b) -> [Change b]
<&&> (SrcSpanAnnA
-> HsExpr GhcPs -> GenLocated SrcSpanAnnA (HsExpr GhcPs)
forall l e. l -> e -> GenLocated l e
L SrcSpanAnnA
lexpr)
                    [Change (GenLocated SrcSpanAnnA (HsExpr GhcPs))]
-> (GenLocated SrcSpanAnnA (HsExpr GhcPs) -> IPBind GhcPs)
-> [Change (IPBind GhcPs)]
forall a b. [Change a] -> (a -> b) -> [Change b]
<&&> (XCIPBind GhcPs
-> XRec GhcPs HsIPName -> LHsExpr GhcPs -> IPBind GhcPs
forall id.
XCIPBind id -> XRec id HsIPName -> LHsExpr id -> IPBind id
IPBind XCIPBind GhcPs
bext XRec GhcPs HsIPName
lname)
                    [Change (IPBind GhcPs)]
-> (IPBind GhcPs -> GenLocated SrcSpanAnnA (IPBind GhcPs))
-> [Change (GenLocated SrcSpanAnnA (IPBind GhcPs))]
forall a b. [Change a] -> (a -> b) -> [Change b]
<&&> (SrcSpanAnnA
-> IPBind GhcPs -> GenLocated SrcSpanAnnA (IPBind GhcPs)
forall l e. l -> e -> GenLocated l e
L SrcSpanAnnA
lbind)
                    [Change (GenLocated SrcSpanAnnA (IPBind GhcPs))]
-> (GenLocated SrcSpanAnnA (IPBind GhcPs)
    -> [GenLocated SrcSpanAnnA (IPBind GhcPs)])
-> [Change [GenLocated SrcSpanAnnA (IPBind GhcPs)]]
forall a b. [Change a] -> (a -> b) -> [Change b]
<&&> (\GenLocated SrcSpanAnnA (IPBind GhcPs)
b -> [GenLocated SrcSpanAnnA (IPBind GhcPs)]
h [GenLocated SrcSpanAnnA (IPBind GhcPs)]
-> [GenLocated SrcSpanAnnA (IPBind GhcPs)]
-> [GenLocated SrcSpanAnnA (IPBind GhcPs)]
forall a. [a] -> [a] -> [a]
++ [GenLocated SrcSpanAnnA (IPBind GhcPs)
b] [GenLocated SrcSpanAnnA (IPBind GhcPs)]
-> [GenLocated SrcSpanAnnA (IPBind GhcPs)]
-> [GenLocated SrcSpanAnnA (IPBind GhcPs)]
forall a. [a] -> [a] -> [a]
++ [GenLocated SrcSpanAnnA (IPBind GhcPs)]
t)
                -- _ -> []
            )
            String
"The removed binding is invalid."
            ChangeType
Removal
        ))
        [Change [GenLocated SrcSpanAnnA (IPBind GhcPs)]]
-> ([GenLocated SrcSpanAnnA (IPBind GhcPs)] -> HsLocalBinds GhcPs)
-> [Change (HsLocalBinds GhcPs)]
forall a b. [Change a] -> (a -> b) -> [Change b]
<&&> (XHsIPBinds GhcPs GhcPs -> HsIPBinds GhcPs -> HsLocalBinds GhcPs
forall idL idR.
XHsIPBinds idL idR -> HsIPBinds idR -> HsLocalBindsLR idL idR
HsIPBinds XHsIPBinds GhcPs GhcPs
ext (HsIPBinds GhcPs -> HsLocalBinds GhcPs)
-> ([GenLocated SrcSpanAnnA (IPBind GhcPs)] -> HsIPBinds GhcPs)
-> [GenLocated SrcSpanAnnA (IPBind GhcPs)]
-> HsLocalBinds GhcPs
forall b c a. (b -> c) -> (a -> b) -> a -> c
. XIPBinds GhcPs -> [LIPBind GhcPs] -> HsIPBinds GhcPs
forall id. XIPBinds id -> [LIPBind id] -> HsIPBinds id
IPBinds XIPBinds GhcPs
xbind)
    -- _ -> []
-- The other cases (`EmptyLocalBinds`, and extensions) do not need to be considered 
enumerateChangesInLocalBinds HsLocalBinds GhcPs
_ SrcSpan
_ = []