Lots of Linux configuration files are peppered with comments. Mostly that’s helpful, but sometimes we just want to see what the configuration settings are.
Simple Solution
Stripping out the comments could be done with a short shell script:
#!/bin/bash FILE=$1 grep -v ^$ $FILE|grep -v ^[[:space:]]*#|grep -v ^\;
That strips out lines that:
- are blank
- start with a hash (#), possibly preceded by one or more spaces
- start with a semicolon (;), used to delimit comments in some files (for example,
php.ini
files)
But it isn’t perfect: it invokes grep three times, and it can’t process input from standard input, so it can’t be fed via the pipe (|) character.
Improved Version
I use this version, saved as /usr/local/bin/decomment
and made executable:
#!/bin/bash [ $# -ge 1 -a -f "$1" ] && INPUT="$1" || INPUT="-" egrep -v '^($|[[:space:]]*#|\;)' $INPUT
Here it is in action:
$ cat test.conf # Sample configuration file # my_param = 1 my_param = 2 verbose = 1 $ decomment test.conf my_param = 2 verbose = 1 $ grep param test.conf # my_param = 1 my_param = 2 $ grep param test.conf | decomment my_param = 2
How It Works
The first part of the first line which is inside the brackets is a test:
[ $# -ge 1 -a -f "$1" ]
That tests whether the number of items on the command line is greater than one – in other words, whether a file is specified after the script name – and whether the item specified after the command is a regular file that is readable. That expression will evaluate to either true or false.
Consider all of the first line now:
[ $# -ge 1 -a -f "$1" ] && INPUT="$1" || INPUT="-"
If the test to see whether a readable, regular file has been specified returns true, the symbol INPUT
will be set to the filename. If the test returns false, INPUT will be set to a dash character.
The second line searches for all lines that don’t match a regular expression. The regular expression is:
'^($|[[:space:]]*#|\;)'
This matches:
- start-of-line (
^
) followed by - end-of-line (
$
) OR - any amount of whitespace (including none) followed by a hash (
[[:space:]]*#
) OR - a semicolon, which needs to be delimited from the shell with a backslash (
\;
)
Those matches represent comments or blank lines, so returning all lines that don’t match will strip all blank lines and comments.
The last part specifies where to read the input from ($INPUT
). That’s set to either the filename or the dash (minus) sign. In the latter case, egrep
will read from the standard input (stdin
).
Could this Linux Tip be improved? Let us know in the comments below.
Brilliant. The best way of decommenting I’ve seen.
Many thanks.