1

我有以下构建系统

module Main where

import Development.Shake

main :: IO ()
main = shakeArgs shakeOptions $ do

  "a" %> \out -> do
    need ["a.in"]
    cmd_ "sleep" "10"
    cmd "touch" [out]

我用它构建stack build和运行stack exec myShake -- --progress a

如果我做了一个干净的构建然后touch a.in再次运行,shake 会向我显示非常错误的进度预测。有时它会预测 1000 分钟甚至更多。

(因为我每 5 秒在终端的标题栏中得到一个进度预测,如果我理解正确,我在这里只讨论第一个进度预测,因为这是我在这个构建系统示例中得到的唯一一个。)

我将 lts-9.6 与堆栈和摇动版本 0.16 一起使用(通过 git + stack.yaml 中的包中的条目)。

4

2 回答 2

1

可以在以下位置找到有关进度如何工作的文档progressDisplay

当前的实现是预测剩余时间(基于timeTodo)和已经完成的工作(timeBuilt)。然后将百分比计算为remaining / (done + remaining),而剩余时间通过按此构建中观察到的工作速率缩放剩余时间来计算,大致为done / time_elapsed

在只做一件事的非常短的构建系统的情况下,工作率通常是垃圾 - 所以你最终用一个随机数(可能是一个大数字,以获得1000 米)。

改变工作速率的想法是,有时您在笔记本电脑上使用电池电源与主电源,有时您传递不同的并行标志。至少在开始时,Shake 很可能应该使用一个或多个线程作为工作速率的近似值。

于 2017-10-01T22:36:30.783 回答
1

看起来第一个进度估计消息通常是无用的。对于非平凡的构建系统,这应该不是问题,因为它们花费的时间超过五秒。

使用这个构建系统--progress=1可以看到,第一个估计是这样的,但其他的会变得更好:

module Main where

import Development.Shake

main :: IO ()
main = shakeArgs shakeOptions $ do
  mapM_ (\i ->
    ("a." ++ show i) %> \out ->
      do
        need [out ++ ".in", "a." ++ show (i-1)]
        cmd_ "sleep" "1"
        cmd "touch" [out])
    [1 .. 10]

  "a.0" %> \out -> do
    need ["a.0.in"]
    cmd_ "sleep" "1"
    cmd "touch" [out]

要尝试这个,你需要做

for i in $(seq 0 10); do touch a.$i.in; done

在您与此示例构建系统一起使用的工作目录中。

于 2017-09-27T19:45:30.880 回答