Capturing screen shots and program interaction on UNIX and Linux systems: Part 1, Program interaction

Saving program output, prompts, error messages, and user input

Taking screen shots and capturing interaction between a program and user is something that all technical writers, most developers, and many technical marketing staff need to do. Modern UNIX® systems provide a number of different tools to capture the text-oriented interaction between a user and a specific program and to capture graphical screens and single windows. This article, the first of three, focuses on different ways to keep a record of the interaction between a user and a command-line application. Capturing user input and program output is valuable, not just for internal or external documentation, but also for use as a common debugging mechanism for many application developers.

William von Hagen, Systems Administrator, Writer, WordSmiths

William von Hagen has been a writer and UNIX systems administrator for more than 20 years and a Linux advocate since 1993. Bill is the author or co-author of books on subjects such as Ubuntu Linux, Xen Virtualization, the GNU Compiler Collection (GCC), SUSE Linux, Mac OS X, Linux file systems, and SGML. He has also written numerous articles for Linux and Mac OS X publications and Web sites. You can reach Bill at wvh@vonhagen.org.



22 June 2010

Also available in Chinese

Why capture command-line input and output?

The online reference information for many command-line UNIX and Linux® commands (the man page) is the primary source of information about these commands. All man pages are supposed to explain all the options that are available for a given command and many provide examples of associated program output, including any program prompts and associated user input.

To obtain this information, someone has to create those examples. Reading the source code to see every possible prompt to the user and the scenarios it displays is usually less functional than simply running the program to see what it does. To convert this experimentation into documentation, the developers (or writers who create reference information for an application) find it useful to keep a complete record of program input, prompts for information that are displayed by an application, and user input in response to those prompts.

Capturing a user's interaction with a command-line application is not just a writing task. Most developers of command-line applications use the C programming language's printf() command (or its equivalent in other languages) as their initial debugging tool, using it to display the contents of different variables and data structures throughout an application. Depending on the amount of information displayed, it's usually easiest to capture this output in a file for subsequent examination and analysis. Similarly, system administrators often like to keep a step-by-step record of interactive system or server configuration and initialization.

The next sections of this article explore various ways of capturing user interaction with a command-line application, ranging from using features included in all UNIX and Linux shells to using specific tools to automate capturing this type of information.

Capturing output and error messages

UNIX and Linux systems make it easy to capture program output and errors in separate files using capabilities that are built into the command interpreters, known as shells, that are used on those systems. These capabilities, known as shell redirection, enable users to redirect program output (known as standard output, or stdout to its friends) and program error output (known as standard error or stderr) to specific files or other destinations by using angle bracket characters or numeric identifiers. Different shells use slightly different syntax to capture program output and error messages, as shown in the following list:

  • Writing standard output from the ls program to the file1 file in the /bin/sh, /bin/bash, /bin/csh, and /bin/ksh shells:
    	ls > file1
  • Writing error output from the ls program to the file1 file in the /bin/sh, /bin/bash, /bin/csh, and /bin/ksh shells:
    	ls 2> file1

    (There is no easy way to redirect only error messages to a file if you are using the /bin/csh shell.)

  • Writing both standard and error output from the ls program to the file1 file in the /bin/sh, /bin/bash, /bin/csh, and /bin/ksh shells:
    	ls &> file1
  • Writing standard output from the ls program to the file1 file and error output from this command to the file2 file in the /bin/sh, /bin/bash, and /bin/ksh shells:
    	ls 1> file1 2> file2

Shell redirection can be handy in capturing standard program output, error messages from a program, or both to text files. However, this isn't sufficient if what you really want to do is to capture a user's interaction with a program. For that, you can take advantage of the shell's interactive capabilities and an additional type of output redirection known as a pipe.

Capturing program interaction using an interactive shell

The previous section showed how to write specific aspects of a user's interaction to specific files, which is helpful if you're trying to capture debugging output, program usage information, and so on. However, if you're writing documentation for an application or simply keeping a record of using or experimenting with an application, you want to see what you're providing as input to the program (an example of what is known as standard input or stdin), and the application's reaction to that input. The last two sections of this article discuss some applications that are designed for that purpose. This section focuses on how you can do that using only your favorite shell, an additional type of shell redirection known as a pipe, and a standard UNIX or Linux utility known as tee.

In UNIX and Linux shells, a pipe is represented by the "|" symbol and connects the standard output of one command to the standard input of another. The UNIX or Linux tee application does what its name suggests if you're familiar with various plumbing connectors—it splits its input into two different streams. One of these remains standard output, while the other is a file whose name you specify on the command line. Therefore, you can use the combination of a pipe and the tee command to combine redirecting the output of a program into a file and see that output. For example, the following command displays both the output of the ls /etc command and captures the standard output of that command in the ls.out file:

    ls /etc | tee ls.out

You can also redirect standard error and standard output via a pipe on the command line by using the "|&" characters. For example, the following command both displays the output and any error messages of the ls /etc command and uses the tee command to capture the output and error messages in the ls.out file:

    ls /etc |& tee ls.out

You can combine redirection of standard output and standard error via a pipe, the tee command, and your favorite shell's interactive mode to capture all input, output, and error messages to a file using a command such as the following:

    bash -i |& tee output_file.txt

This command executes the Bash shell in interactive mode, meaning that it is essentially a shell that you can interact with until you explicitly terminate it. The command uses the "|&" characters to redirect all the output and error messages of that shell to the tee command, which both displays all output and error messages and saves a copy of everything to the output_file.txt file. When you're done executing any commands that you want to capture your interaction with, you can type the exit command (or the Control-d key combination on most systems) to terminate the shell. The output_file.txt file contains a complete record of anything you typed, any output from the programs you ran, and any error messages that those commands displayed—exactly as it looked while you were executing those commands.

Using the script command

While UNIX and Linux commands such as bash -i |& tee output_file.txt aren't really that complex, it can be a hassle to type them, remember the correct order of the "|" and "&" characters, remember the tee command, and so on. A much simpler solution that is available on most UNIX and Linux systems is the script command, which does all that for you. The script command starts a sub-shell and saves a copy of everything you type, all output from any programs that you run, and any errors that those programs generate to an output file. If you don't specify the name of the file that you want to save everything in, the script command creates a file called typescript, but you can also specify the name of the file that you want to write to on the command line. For example, the following command captures everything you type, all program output, and any error messages to the output_file.txt file:

    script output_file.txt

Similar to using an interactive shell, as discussed in the previous section, you exit the script command and close its output file by typing the exit command (or the Control-d key combination on most systems).

If you compare the contents of an output file produced by the interactive shell mechanism discussed in the previous section and one produced by using the script command, you immediately notice that files produced by the script command usually contain control characters, which are characters such as backspace, return, special characters used to display fancy prompts, and characters used if you edit a previous shell command. The output files created by the script command contain these characters because they contain an exact record of everything you type, not how it is interpreted by the shell. Output files produced using the interactive shell mechanism discussed in the previous section don't contain these characters, because they contain what is eventually forwarded to the shell after control characters, such as backspace and return, are processed.

It's easy enough to clean up a script output file using your favorite text editor, and a variety of cleanup scripts are available on the web. My favorite cleanup mechanism is from the Perl Monks website and uses a combination of a simple Perl command and the standard UNIX and Linux col command, which filters control characters out of its input, to clean up the output files produced by the script command. For example, to create a clean copy named output_file.txt.clean of a script output file named output_file.txt, you execute the command shown in Listing 1.

Listing 1. Cleaning up script output
    cat output_file.txt | \
      perl -pe 's/\e([^\[\]]|\[.*?[a-zA-Z]|\].*?\a)//g' |\
        col -b > output_file.txt.clean

If you do this sort of thing often, you probably want to create a small shell script to automate this process just in case you have problems typing the Perl substitution command in the second line. Listing 2 is a simple shell script that does this.

Listing 2. A shell script for cleaning up script output
    #!/bin/bash

    if [ $# -ne 2 ] ; then 
      echo "Usage: cleanup script-file output-file"
      exit
    fi

    cat $1 | \
      perl -pe 's/\e([^\[\]]|\[.*?[a-zA-Z]|\].*?\a)//g' |\
        col -b > $2

Shell redirection, the interactive shell command discussed in the previous section, and the script command discussed in this section are all mechanisms for capturing program interaction that you can use on almost every UNIX and Linux system. However, some UNIX systems provide additional tools for capturing program interaction. Those tools provide additional capabilities that can be useful in special situations, as discussed in the next section.

Platform-specific text-capture utilities

Most UNIX and Linux systems simply provide the script command to automate capturing program interaction, but AIX operating systems provide a handy utility, cleverly called capture, that enables you to write a specific screen's worth of text to a file. This is helpful when you want to show an example of running a command that manipulates the screen, such as a text editor. Trying to capture an example of using the vi editor to a file using shell redirection or the script command creates an output file that contains many control characters and is essentially unintelligible.

If you do not specify the name of a specific file to write to on the command line, the AIX capture command creates a file called screen.out. Starting the capture command creates a shell in which you can execute any commands that you want until the screen shows exactly what you want to capture. At that point, typing the Control-p key combination writes the contents of the screen to your output file. To terminate the capture command, simply type the exit command (or Control-d on most systems).

When using the capture command, it's important to remember that it doesn't capture the text on the screen until you type Control-p and that typing Control-p multiple times simply overwrites your output file unless you start the capture command with the -a option to tell it to append to the output file rather than overwrite it.

Summary

Capturing your interaction with a program is a surprisingly common task. Though UNIX and Linux shells provide built-in mechanisms for writing specific portions of that interaction to text files, using an interactive shell or the script command produces single output files that provide a complete sequential record of program interaction. The mechanisms for producing these output files (and cleaning them up, when necessary) are useful tools for almost any UNIX or Linux writer, developer, or system administrator.

The next article in this series will discuss standard tools for capturing images that show the entire screen or a specific window on UNIX and Linux systems. It will also explain how to convert those images into a variety of standard graphics formats.

Resources

Learn

Get products and technologies

  • The script command is installed by default on most UNIX and Linux systems, and is part of the bsdutils package on Linux systems, which is itself part of the util-linux package on Linux systems. You can get the source code for this package as part of the standard packages for your system or from ftp://ftp.us.kernel.org/pub/linux/utils/util-linux/.
  • The Perl Monks Web site provided the incantation used in this article to clean up script output and has many other great tips for Perl fans.

Discuss

Comments

developerWorks: Sign in

Required fields are indicated with an asterisk (*).


Need an IBM ID?
Forgot your IBM ID?


Forgot your password?
Change your password

By clicking Submit, you agree to the developerWorks terms of use.

 


The first time you sign into developerWorks, a profile is created for you. Information in your profile (your name, country/region, and company name) is displayed to the public and will accompany any content you post, unless you opt to hide your company name. You may update your IBM account at any time.

All information submitted is secure.

Choose your display name



The first time you sign in to developerWorks, a profile is created for you, so you need to choose a display name. Your display name accompanies the content you post on developerWorks.

Please choose a display name between 3-31 characters. Your display name must be unique in the developerWorks community and should not be your email address for privacy reasons.

Required fields are indicated with an asterisk (*).

(Must be between 3 – 31 characters.)

By clicking Submit, you agree to the developerWorks terms of use.

 


All information submitted is secure.

Dig deeper into AIX and Unix on developerWorks


static.content.url=http://www.ibm.com/developerworks/js/artrating/
SITE_ID=1
Zone=AIX and UNIX, Java technology
ArticleID=497462
ArticleTitle= Capturing screen shots and program interaction on UNIX and Linux systems: Part 1, Program interaction
publish-date=06222010