Ghc 7.6限定导入、ghc-pkg hide 和 ghc 的 -package 选项允许您在导入文件和导入文件之间无缝添加一层。
例子:
使用您自己的 Data.Char 创建一个包,使用标准 .cabal 文件和 cabal 安装。
{-# language PackageImports #-}
module Data.Char (
toUpper
, Char
, String
-- ... Export every else from "Base" Data char because the limitation of
-- the current export facility you can not use
-- module Data.Char hiding (toUpper)
) where
import "base" Data.Char hiding (toUpper)
import qualified "base" Data.Char as OldChar
toUpper :: Char -> IO Char
toUpper c = do
print "Oh Yeahhhhhhhhh"
return $ OldChar.toUpper c
隐藏基本包ghc-pkg hide base
——在这种情况下隐藏了许多模块,如果需要,您需要将它们全部包装起来。
> ghci -XNoImplicitPrelude -- We need language flag because the Prelude is in
-- base and I did not make a wrapped Prelude
ghci> import Data.Char
ghci> toUpper 'c' -- The wrapped function
"Oh Yeahhhhhhhhh"
'C'
ghci> isSpace ' ' -- The unwrapped normal Data.Char function
True
现在您可以使用模板 Haskell 来包装您的函数并调用您需要获取外部信息的任何 IO 操作。用户甚至不需要更改任何函数调用或模块导入,只需在名称中添加“内部”即可。
能够无缝地封装模块接口还意味着您可以更改导入模块的植入,而无需接触包/模块代码或您正在使用的现有代码库;你只需要做一个中间层。
编辑对问题的回复:
当然可以,ghc-api 可以让您完成所有这些工作,但是要复杂得多,比我想要的例子更少,而且我似乎看到更多人在使用它时遇到困难,然后是成功案例。
- 用于评估代码提示
- 建议使用插件来动态加载模块
- haskell-src-ext 建议用于解析和更改代码。这就是style-haskell用来对代码进行小修改的方法,是你最好的选择。据报道,它涵盖了 Haskell 2010 的大部分(全部?),以及许多但不是所有 GHC 扩展,如果您不喜欢我提供的第一个解决方案,它可能是您最好的选择。
据我所知,GHC-API 是唯一一个与 GHC 兼容代码完全兼容的代码,但要复杂得多,文档记录较少,而且更有可能从 GHC 版本更改为 GHC 版本,或者至少没有承诺会根据我有限的经验,是一样的。我建议将一个模块放在中间,因为它似乎是最快的获得良好的测试覆盖率,需要最少的新知识并满足我从你的问题中挑选出来的要求。