在我的项目中,我有一组包含package.yaml
文件的子目录,例如:
A/package.yaml
B/package.yaml
C/package.yaml
如果我运行hpack A/package.yaml
,则文件A/A.cabal
被(重新)生成。此类目录的列表会随着时间变化,因此我想使用GNU make查找包含package.yaml
文件的所有直接子目录,并使用hpack生成相应的.cabal
文件。
我根据another question尝试了此操作,但没有成功:
HPACK_FILES := $(wildcard */package.yaml)
PKG_DIRS := $(subst /,,$(dir $(HPACK_FILES)))
CABAL_FILES := $(addsuffix .cabal,$(join $(dir $(HPACK_FILES)),$(PKG_DIRS)))
test:
@echo $(CABAL_FILES)
update-cabal: $(CABAL_FILES)
%.cabal: package.yaml
hpack $<
但是,make update-cabal
说什么也没做。 make test
确实输出正确的阴谋文件。我该如何解决?
干杯!
答案 0 :(得分:1)
问题是这样的:
%.cabal: package.yaml
没有文件package.yaml
。这些文件被命名为A/package.yaml
之类的东西。那不是同一回事。
由于先决条件不存在,make决定此模式规则不匹配,因此它继续寻找可能能够构建目标的另一条规则。它找不到能建立目标的任何规则,因此make说没事做,因为所有输出文件已经存在。
不幸的是,make并不是一件容易的事,因为make最适合由带有扩展名或类似名称的文件名捆绑在一起的输入和输出文件。尤其是,要处理多次重复可变部分的关系(例如,A/A.cabal
重复A
的关系)非常困难。在make中没有简单的方法。
您必须使用eval
之类的高级功能来执行此操作。像这样:
# How to build a cabal file
%.cabal:
hpack $<
# Declare the prerequisites
$(foreach D,$(dir $(HPACK_FILES)),$(eval $D/$D.cabal: $D/package.yml))