blog icon indicating copy to clipboard operation
blog copied to clipboard

Executing shell scripts through QSH (using bash)

Open worksofliam opened this issue 5 years ago • 2 comments

Lately, I've been needing to call shell scripts through bash periodically and it can be a real pain doing it with QP2TERM. Instead, you can use QSH to call bash to execute your shell script.

Prerequisits

  • You need bash, which comes installed automatically when you install yum.
  • I am using vscode to work with stuff in the IFS. Some people in the IBM i world didn't know it was free so go take a look at it.
    • With vscode, I am also using the SSH FS extension which can be found in the marketplace. This extension allows me to connect to my IBM i over SSH to work with files in the IFS.

Creating our script

In vscode, when connected to your system go ahead and create a new file and give it a name but make sure it ends with .sh so you can see it's a shell. (extension doesn't really matter, but .sh indicates a shell script)

image

Here's my simple shell script:

#!/QOpenSys/pkgs/bin/bash

echo Hello world!

Before we go on, you need to make sure the new line characters are just LF and not CRLF. In the bottom right of vscode you can see a button that says either CRLF or LF - you want to make sure you change it to LF for your shell script and then resave the file.

image


Calling our script through QSH

Calling through QSH is actually fairly easy. The QSH command on IBM i takes a single parameter which is the command to execute. We are going to pass it the path to bash and then the path to our shell script, which just tells bash to execute our shell script. The script will execute inside of pase.

QSH CMD('/QOpenSys/pkgs/bin/bash test.sh')

image

It does also mean you can submit your shell scripts to batch using SBMJOB (or even call one in a scheduled job):

SBMJOB CMD(QSH CMD('/QOpenSys/pkgs/bin/bash test.sh')) JOB(QSHJOB)

image

If you take option 8 and work with the spool files, QSH actually writes all the output to a spool file.

image

image

Calling our script through pase

Because just created our script, it won't execute when we try to run it. This is because we haven't marked it as an executable. We can do this with chmod. You can read more about what marking as executable means here.

bash-4.4$ ls
test.sh
bash-4.4$ ./test.sh
bash: ./test.sh: Permission denied
bash-4.4$ chmod +x test.sh
bash-4.4$ ./test.sh
Hello world!

Use cases

You can do so much with a shell script:

  • Execute a Python or Node.js script
  • Restart a named pm2 service
  • Work with acme.sh to check if your Let's Encrypt certs will expire
  • Delete temporary files on a schedules basis

worksofliam avatar Jul 10 '19 15:07 worksofliam

Can you show an example of restarting a named PM2 service with QSH? I can start and stop one from a CLP with SBMJOB, but it's a bit quirky. Thank you.

betsonserviceportal avatar Nov 07 '19 00:11 betsonserviceportal

Hey Liam,

According to IBM (https://www.ibm.com/support/pages/how-call-pase-commandsscripts-command-line-cl-program-or-submitted-job), the script should be invoked this way:

QSH CMD('/QOpenSys/usr/bin/sh -c "/QOpenSys/bin/script.sh"')

Presumably you could use any shell; I tried it like this and it worked

QSH CMD('/bin/bash -c "~/myscript.sh"')

but I also tried it the way you did (without specifying a shell) and it also worked. Perhaps the shebang (#!/bin/bash) at the start of my script forces it to start a Bash shell, anyway?

Do you have any knowledge on how this actually works?

Thanks!

JeffBerman avatar Mar 11 '20 22:03 JeffBerman