如何判断是否正在从交互式shell运行makefile?

时间:2010-11-23 00:14:52

标签: unix shell makefile gnu-make

我有一个运行命令的makefile可能需要一段时间。如果构建是从交互式shell启动的话,我希望这些命令是健谈的,但如果没有(特别是cron)则更安静。类似于(伪代码)的东西:

foo_opts = -a -b -c
if (make was invoked from an interactive shell):
    foo_opts += --verbose

all: bar baz
    foo $(foo_opts)

这是GNU make。如果我正在做的事情的具体细节,我可以编辑问题。

5 个答案:

答案 0 :(得分:7)

不是严格确定是否从交互式shell调用它,而是对于将输出重定向到文件的cron作业,此问题的答案与{{3}的答案相同}:

if [ -t 0 ]
then
    # input is from a terminal
fi

编辑:使用它在Makefile中设置变量(在GNU make中,即):

INTERACTIVE:=$(shell [ -t 0 ] && echo 1)

ifdef INTERACTIVE
# is a terminal
else
# cron job
endif

答案 1 :(得分:4)

http://www.faqs.org/faqs/unix-faq/faq/part5/section-5.html

5.5)如何判断我是否正在运行交互式shell?

  In the C shell category, look for the variable $prompt.

  In the Bourne shell category, you can look for the variable $PS1,
  however, it is better to check the variable $-.  If $- contains
  an 'i', the shell is interactive.  Test like so:

      case $- in
      *i*)    # do things for interactive shell
              ;;
      *)      # do things for non-interactive shell
              ;;
      esac

答案 2 :(得分:4)

我认为你不能轻易找到答案。我建议采用另一种策略,可能是通过压缩cron作业的冗长输出。我希望使用像这样的makefile来做到这一点:

VERBOSE = --verbose

foo_opts = -a -b -c ${VERBOSE}

all: bar baz
    foo $(foo_opts)

然后,在cron作业中,指定:

make VERBOSE=

VERBOSE的命令行规范会覆盖makefile中的那个(并且不能被makefile更改)。这样,你设置一次并多次使用的专门任务(cron作业)将在没有详细输出的情况下完成;构建的一般任务将大致完成(除非您选择覆盖命令行上的详细信息)。

这种技术的一个小优点是它可以与make的任何变体一起使用;它不依赖于任何GNU Make工具。

答案 3 :(得分:0)

我不太确定“互动”是什么意思。你的意思是你有一个有效的/dev/tty吗?如果是这样,那么你可以检查一下。我们大多数人在stdin上检查isatty,因为它回答了我们想知道的问题:是否有人在那里输入内容。

答案 4 :(得分:0)

请注意:您还可以看到the related discussion我在Makefile中检测到STDOUT的重定向。

我相信这对这个问题的读者有帮助 - 执行摘要:

-include piped.mk

all:    piped.mk
ifeq ($(PIPED),1)
    @echo Output of make is piped because PIPED is ${PIPED}
else
    @echo Output of make is NOT piped because PIPED is ${PIPED}
endif
    @rm -f piped.mk

piped.mk:
    @[ -t 1 ] && PIPED=0 || PIPED=1 ; echo "PIPED=$${PIPED}" > piped.mk

$ make
Output of make is NOT piped because PIPED is 0

$ make | more
Output of make is piped because PIPED is 1

在我的回答中,我解释了为什么[-t 1]必须在一个动作而不是变量赋值中完成(如此处的推荐答案),以及有关重新评估a的各种缺陷。生成Makefile(即上面的piped.mk)。

此问题中的术语 interactive 似乎意味着重定向STDIN ...在这种情况下,在上面的代码中用[ -t 1 ]替换[ -t 0 ]应该按原样运行。

希望这有帮助。