Go Back   The macosxhints Forums > OS X Help Requests > UNIX - General



Reply
 
Thread Tools Rate Thread Display Modes
Old 11-07-2009, 07:16 PM   #1
Hal Itosis
MVP
 
Join Date: Apr 2002
Posts: 2,112
getting awk's printf to produce styled text

I had more-or-less given up on getting awk's printf to (for example) print bold text.
Stuff that works with Bash's builtin printf does not fly in awk:

$ echo 'text to stylize' |awk '{ printf "\e[1m %s\e[0m\n", $0 }'
e[1m text to stylizee[0m

Today i found a way though. Here's a snippet from my shell script to demonstrate...
Code:
	:
	:
	done |
	awk  -v nam=$1 -v lst=$list -v bold=$'\e[1m' -v norm=$'\e[0m'  '{
		siz+=$1
		if (lst == "true") print
	}
	END {	if (NR > 0)
		{
			if (lst == "true") print ""
			printf bold
			printf("%8.2f megs for %5d items in %s\n", siz/1024, NR, nam)
			printf norm
		}
		system("")
	}'
[i.e., only the red text highlighting the bold and norm variables contains the relevant code]

If anyone knows another (perhaps better?) solution, consider this post a request for help.
Otherwise, i hereby offer this method to those scripters who had previously given up hope.

-HI-
Hal Itosis is offline   Reply With Quote
Old 11-08-2009, 05:49 PM   #2
Hal Itosis
MVP
 
Join Date: Apr 2002
Posts: 2,112
While the above works great just printing to the terminal screen, there may be times when awk's output (and/or the shell script's output) may need to be piped to some external command. In such cases, having the escape codes (control chars) going out with the data will likely be undesirable. Here is awk's equivalent of >&2 to divert that junk to the error stream...

printf bold > "/dev/stderr"
printf ("important stuff %s\n", $var)
printf norm > "/dev/stderr"
Hal Itosis is offline   Reply With Quote
Old 11-09-2009, 02:35 AM   #3
dmacks
All Star
 
Join Date: Dec 2004
Posts: 594
...which then junks up stderr, which could be being redirected somewhere else. One trick I've seen is to test if output is going to a terminal and then only do styled text if so. Pseudocode:

Code:
if (isterm(STDOUT)) {
  bold='\e[1m'
  norm='\e[0m'
} else {
  bold=''
  norm=''
}

printf ("%simportant stuff %s%s\n", $bold, $var, $norm)
In perl, the isterm test is 'POSIX::isatty(fileno STDOUT)'.
dmacks is offline   Reply With Quote
Old 11-09-2009, 03:49 AM   #4
Hal Itosis
MVP
 
Join Date: Apr 2002
Posts: 2,112
Thumbs up

Okay, cool... i like that. Thanks.

Just curious though...
Quote:
Originally Posted by dmacks
...which then junks up stderr,

Why care? (I.e., if someone's reading the error stream out of *my* script at some point, they need to accept whatever i put there. It's not supposed to be regarded as 'data'.).


Quote:
Originally Posted by dmacks
which could be being redirected somewhere else.

Like a log file i suppose? Well... all sorts of silliness [as well as "legitimate" error messages] gets dumped there frequently. It doesn't matter [does it?]. I mean, at any given time the error stream could get *flooded* with messages from commands talking about: 'permission denied' or 'no such file', etc., etc. How can anyone ever depend on it being in any particular state? Someone might mistakenly call my script with a -h option (and get the help text). Quite deliberately, that text *always* goes out on stderr regardless, so that no one could possibly interpret it as being bad data coming from standard "output."

--

Actually, i have seen some strange things where commands (i think codesign is one) send *data* out on both streams. [data, on both 1 and 2 simultaneously, within a single operation... not data on 1 and error on 2.] I would tend to regard that practice as either questionable, confusing or unnecessary. [We try to capture it... and: "hey, what?... it's only half there???"] So we have to put a 2>&1 before the pipe to bring them together, for that one operation. And naturally it's not documented on the man page or anything. We have to 'discover' it.

Anyway, your addition certainly salvages the situation for folks that use fd2 for extra data. I just think if someone wants to get fancy, then open a new stream/descriptor. Don't be using stderr for "stereo" data (or whatever). Or... at least expect other scripts to do things differently, which seems to be the universal reality anyway.

Again, i appreciate the feedback. Thanks.

Last edited by Hal Itosis; 11-09-2009 at 03:51 AM.
Hal Itosis is offline   Reply With Quote
Reply

Thread Tools
Display Modes Rate This Thread
Rate This Thread:

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off

Forum Jump


All times are GMT -5. The time now is 05:10 PM.


Powered by vBulletin® Version 3.8.4
Copyright ©2000 - 2009, Jelsoft Enterprises Ltd.
Site design © Mac Publishing LLC; individuals retain copyright of their postings
but consent to the possible use of their material in other areas of Mac Publishing LLC.