Unix Tip: Am I interactive?: Take three

By Sandra Henry-Stocker, ITworld.com |  Operating Systems Add a new comment

Send in your Unix questions today!


See additional Unix tips and tricks


If there's one thing that every Unix systems administrator knows, it's that there's always more than one way to get something done. Some ways of solving a problem are more efficient than others. Other ways of solving a problem are easier to understand or extend to similar, but not identical, situations. But there are always multiple solutions to a task.

In recent columns, we have looked at two very different methods of determining whether or not a script was being run interactively or through cron. In the first, we used the Solaris ptree command to determine the parentage (or "ancestry") of a task. If a process was started by crond or its parent process was started by crond, we would know that it was run through cron. In the second, we used the tty command to identify the controlling terminal. In fact, just knowing that there is a controlling terminal (such as /dev/ttyp1), we know a process is being run interactively; cron jobs do not have controlling terminals. In this third and last method, we will use a very simple conditional test, built into the shell, to determine whether a process is interactive. This simple test, -t, is in the same family of tests as -f (testing if there is a file with the specified name) and -d (testing if there is a directory with the specified name). The -t test determines whether the specified file descriptor is associated with a terminal. Let's look at a couple of examples to see how this works.

On the command line, we can use the -t test like this:

$ if [ -t 0 ]; then
> echo interactive
> fi
interactive

Alternately, we can turn the command into a simple script. In this example, we're looking at a Bourne shell script, though this same syntax should work with bash and ksh. We are using the -t test to determine whether there is a terminal associated with file descriptor 0 (i.e., standard in). If there is an associated terminal, we print the message "interactive". If there is no associated terminal, we print "non-interactive".

#!/bin/sh
# test0

if [ -t 0 ]; then
   echo interactive
else
   echo non-interactive
fi

Of course, what we need to do next is verify that we get the opposite response when we're not running our script interactively. To run this script through cron and verify that its output will be "non-interactive", we'll set up a cron task like this:

5 * * * * /export/home/shs/test0 > /var/log/test.log

Once the script runs, we should see the word "non-interactive" in our log file, basically demonstarting that standard in for a cron job is not associated with a terminal.

We could also run the same test using syntax like that shown below. While this syntax is more terse, it doesn't lend itself to executing a series of commands. Instead, it works better with single commands or function calls.

test -t 0 && echo "Running interactively" || echo "Running in batch"

Conditional Tests

Simple conditional tests, like -t, can be found in every Unix shell and on every "flavor" of Unix. While the set of such tests that is implemented may vary from system to system or shell to shell, there is enough overlap to make these tests extremely handy in any environment. Here is a list of some of the tests that you are likely to find extremely useful:

-b file, True if file exists and is a block special file.
-c file, True if file exists and is a character special file.
-d file, True if file exists and is a directory.
-e file, True if file exists.
-f file, True if file exists and is a regular file.
-g file, True if file exists and is set-group-id.
-h file, True if file exists and is a symbolic link.
-k file, True if file exists and its ``sticky'' bit is set.
-p file, True if file exists and is a named pipe (FIFO).
-r file, True if file exists and is readable.
-s file, True if file exists and has a size greater than zero.
-t fd,   True if file descriptor fd is open and refers to a terminal.
-u file, True if file exists and its set-user-id bit is set.
-w file, True if file exists and is writable.
-x file, True if file exists and is executable.

The syntax for a conditional test is different in the C shell and tsch. In the sample script below, we've implemented the same simple test in csh:

    Add a comment

    Post a comment using one of these accounts
    Or join now
    At least 6 characters

    Note: Comment will appear soon after you have activated your account.
    Obscene/spam comments will be removed and accounts suspended.
    The information you submit is subject to our Privacy Policy and Terms of Service.

    ITworld LIVE

    Operating SystemsWhite Papers & Webcasts

    White Paper

    Microsoft Enterprise Agreement Program Overview

    Discover how flexible the Microsoft Enterprise Agreement Program is to help you build the right software solution agreement for your business. This paper highlights all the available options-from on-premise software and cloud service solutions, to payment options and enrollment programs, and more.

    White Paper

    Watson - A System Designed for Answers. The future of workload optimized systems design

    Watson is a workload optimized system designed for complex analytics, made possible by integrating massively parallel POWER7 processors and DeepQA technology. Read the white paper about Watson's workload optimized system design.

    See more White Papers | Webcasts

    Ask a question

    Ask a Question