ISO27001:2013
Certified Supplier

FIND OUT MORE

We're an ISO27001:2013 Certified Supplier

blog-post-featured-image

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.

Leave a Reply

Your email address will not be published. Required fields are marked *