我想找到所有' Makefiles'在我的项目中然后生成 规则基于他们。 然而,看起来(故意)没有什么可以逃脱一个行动。 所以,相反,我取消了我的'Makefile'扫描仪到IO操作之前 摇动功能。
main = do
makefiles <- findMakefiles
shake skakeOptions $ generate_rules makefiles
有更好的方法吗?
答案 0 :(得分:1)
首先,我不认为目前的方法存在任何问题。 Shake包本身对内置的Ninja和Makefile解释器采用了类似的方法, 见details about the Makefile interpreter 或the Sake interpreter。只要处理Makefile就足够快 物质(它通常是)然后你基本上写了一个 使用Shake解释您的自定义构建语法,它有效 很好。
有几个原因可以避免这种方法,例如,如果Makefile的处理很昂贵,或者Makefile本身有其他依赖项。在这种情况下,您可以使用newCache
的组合来解析Makefile一次,以及addOracle
,因此规则可以依赖于它们所需的Makefile的子集。然而,这种方法很难实现,因为它基本上强制了一层间接,你必须对generate_rules
的工作方式做出一些假设。 ghc-make包使用此技术(请参阅&#34; makefile&#34;规则并调用newCache
),Shake包中的usingConfigFile
函数使用相同的{{1} } / newCache
模式。
坚持使用原始方法,您可以将addOracle
步骤略微区别开来。你可以这样做:
findMakefiles
这样做的好处是,您可以轻松添加命令行标志以找出Makefile的位置或处理它的选项。 Shake中的Ninja和Makefile系统都支持使用main = shakeArgsWith shakeOptions [] $ \_ -> xs -> do
makefiles <- findMakefiles
let rules = generate_rules makefiles
if null xs then rules else withoutActions rules >> want xs
来覆盖默认值。即使您不想移动--makefile=FILE
,也可以在原始示例中将generate_rules
替换为shake
,这将为您提供命令行处理。