Quering databases by using SQL in shell scripts can make the whole script unreadable. Very often the query is unredable too, due to the variable usage. This situation makes the script-debugging a pain.

Templating simplifies the script by taking out the SQL code from the source code file. J2 is ideally built for that.

Let’s take a simple example:

$> cat sql_in_shell.sh

#!/bin/bash
. oraenv <<< $1

table=$2
col1=$3
val1=$4

sqlplus -s / as sysdba << EOF
select count(*)
from $table
where $col1=$val1
;
exit;
EOF

Ok, this is a simple one, but in real world the queries are much complicated, and variables too…

The execution produces the following output:

$> sql_in_shell.sh MYDBNAME v\$instance instance_name \'MYDBNAME\'

  COUNT(*)
----------
	 1

Doing it like this it is very difficult to find the real query executed by the script…

Let’s use J2 templates.

We put all templates in a template directory and generated sql files in the onrun directory.

$> cat templates/qry.j2
select count(*)
from {{ table }}
where {{ col1 }}={{ val1 }}
;
exit;

The script becomes:

$ cat ./sql_in_shell.sh
#!/bin/bash

#. oraenv <<< $1

echo "$1"

j2_sql="qry.sql"
j2_templ="qry.j2"
export table=$2
export col1=$3
export val1=$4

j2 templates/$j2_templ > onrun/$j2_sql

sqlplus -s / as sysdba @onrun/$j2_sql

The output is the same:

$> sql_in_shell.sh MYDBNAME v\$instance instance_name \'MYDBNAME\'

  COUNT(*)
----------
	 1

Now we have the executed query in the onrun directory:

$ cat onrun/qry.sql
select count(*)
from v$instance
where instance_name='MYDBNAME'
;
exit;

Resources

J2 client can be found here: https://github.com/kolypto/j2cli. The site provides also an excelent documentation.

Ubuntu provides already deb packages and for rpm’s an additional repository must be added following: https://snapcraft.io/install/j2/rhel

Conclusion

Templating brings shell coding in to a more modern world, liberating the code source of difficult to understand variables replacement. More than that, keeping all executed queries, is a best practice and makes the debugging much easier.


Share on