packages feed

haskell-awk-1.1: src/System/Console/Hawk/UserPrelude/Extend.hs

-- | In which the implicit defaults are explicitly added.
module System.Console.Hawk.UserPrelude.Extend
  ( extendModuleName
  , extendImports
  ) where

import Control.Applicative
import Data.Maybe

import Data.HaskellModule
import System.Console.Hawk.UserPrelude.Defaults


-- | We cannot import a module unless it has a name.
extendModuleName :: HaskellModule -> HaskellModule
extendModuleName = until hasModuleName
                       $ addDefaultModuleName defaultModuleName
  where
    hasModuleName = isJust . moduleName


moduleNames :: HaskellModule -> [String]
moduleNames = map fst . importedModules

-- | GHC imports the Haskell Prelude by default, but hint doesn't.
-- 
-- >>> let m name = (name, Nothing)
-- >>> :{
--   let testM exts modules = moduleNames m'
--         where
--           m0  = emptyModule
--           m1  = foldr addExtension m0 exts
--           m2  = foldr addImport m1 modules
--           m' = extendImports m2
-- :}
-- 
-- >>> testM [] []
-- ["Prelude"]
-- 
-- >>> testM [] [m "Data.Maybe"]
-- ["Prelude","Data.Maybe"]
-- 
-- >>> testM [] [m "Data.Maybe", m "Prelude", m "Data.Either"]
-- ["Data.Maybe","Prelude","Data.Either"]
-- 
-- >>> :{
-- testM [] [ ("Data.Maybe", Just "M")
--          , ("Prelude", Just "P")
--          , ("Data.Either", Just "E")
--          ]
-- :}
-- ["Data.Maybe","Prelude","Data.Either"]
-- 
-- >>> :{
-- testM ["OverloadedStrings","NoImplicitPrelude"]
--       [m "Data.Maybe"]
-- :}
-- ["Data.Maybe"]
extendImports :: HaskellModule -> HaskellModule
extendImports = until preludeOk
                    $ addImport unqualified_prelude
  where
    prelude = "Prelude"
    noPrelude = "NoImplicitPrelude"
    unqualified_prelude = (prelude, Nothing)
    
    preludeOk = liftA2 (||) hasPrelude noImplicitPrelude
    hasPrelude        m =   prelude `elem` moduleNames m
    noImplicitPrelude m = noPrelude `elem` languageExtensions m