==========
 shellia
==========

-------------------------------------
library for interactive shell scripts
-------------------------------------

:Author: bernd.schumacher@hpe.com
:Date: 2018-07-26
:Copyright: gpl3
:Version: 0.1
:Manual section: 7
:Manual group: shell library

SYNOPSIS
========

  **. /usr/share/shellia/ia[.interactive|.check|.debug|]**

NAME
====
**shellia** is a library that allows to run **shell** scripts interactive.
The word interactive is the most characteristic adjective for **shellia** and
the shortest abbreviation found for interactive is **ia**.
Such a short abbreviation is needed, because most commands brought by
**shellia** start with this short prefix **ia**.
**shellia** is composed from **shell** and **ia**.

See also **PREFIX** in shellia(3).

DESCRIPTION
===========

**shellia** is a library that allows to run shell scripts silently or
interactive and helps to check errors of commands that are combined in
**steps**.

This makes it easy to familiarize oneself with a shell script that uses
**shellia** and find unexpected behaviour in the shell script.
Also when running the shell script silently **shellia** can check it **step** by
**step**.

Shell scripts often become large with many subfunctions, calling many commands.
This leads to the following problems, where **shellia** can help:

* It is not easy to run only parts of the script, to learn about an existing
  script, to find an error in a script, to change the order of parts of the
  script for testing or to rerun only a part of the script that failed.
* It is not easy to find out, from which part of the script errors, warnings
  or messages that appear on stdout or stderr are created.
  And it is often not clear if output of a shell script is ok and can be
  ignored.
* Often commands are started in a shell script without checking for Errors
  because this would make the scripts too complex.
* Many programs can only enable debug at start time.
  This can result in much debug output, also if only specific debug output
  is needed.

The shellia library can help with the following features.

* run a script or parts of a script interactively
* check each command for unexpected output or returncode
* jump to interactive mode if an error occurs or exit the script
* helps to structure large scripts
* in interactive mode shellia can toggled the debug output level

NOTES
=====

When building a *./script.using.shellia* the following hints may be helpful:

Do not use a single command as a step
-------------------------------------

It is important to find the right size of a **step** to be uses in **shellia**.
The idea of a **step** is not to check the execution of a single command.
Instead a single command can be part of a function, that is called by a **step**.

Input and Output of a step
--------------------------

Each **step** should be interactively runable by an end user of the script.
This means the end user should be able to handle input and output of a **step**.
This often means a **step** should not read stdin or send stdout to another **step**.
For example a backup script could have one **step** to backup /home and another
**step** to backup /usr.
But a **step** that reads data from work disk and another **step** that writes
backup data to a backup disk should better be combined in a single **step**.

Reasonable size of interactive steps
------------------------------------

If the user of the script can not imagine what an interactive **step** does,
this **step** may be to detailed and to small.
If to many errors may happen in the interactive **step**, the **step** may be
to large. For example, if you need to mount an external disk, this should
be a separate interactive **step**. Because this can give errors, if the disk
is not readable. And this errors can again lead to follow up errors.

When to use check option -c and -C
----------------------------------

Both options will check the output and the exit code of a **step**.
All output has to be allowed with extended regular expressions in
**check-mode**.
To be able to control the exit code in the same way, the line
*exit=<exit code>* (with *<exit code>* replace by the exit code),
will be added, if the exit code is nonzero.

With option **-c**, per default every output to **stdout** and **stderr**
is seen as one output and is displayed as an error.
The developer can change this with **ia_stdout** and **ia_ignore**.
This means with **-c** every output is checked, also output that would
normally go to **stdout**.
This makes it easy to find changed output from a command used, e.g.
when upgrading to a new operating system version.

With option **-C**, per default every output to **stdout** is unchanged and
all output to **stderr** is seen as an error.
The devloper can ignore error output with **ia_ignore**.
This means the developer has not to handle **stdout**, which can be
good and bad.

If a **step** calls a programm, that produces *stdout* and *stderr* output,
and it is most important to retain the order of the output,
option **-c** should be used. With option **-c** the output of
both streams would be combined by **shellia** to one stream.
If it is important to know if output is from *stdout* or from
*stderr* to decide if it is an error, option **-C** should be used.


Use --quiet, --silent or similar if available
---------------------------------------------

If commands are used with check option **-c** or **-C**, less
**ia_stdout** or **ia_stderr** lines have to written, if the commands
create less output.

EXAMPLE
=======

For example imagine a backup script, that writes to an external disk,
that should then contain an encrypted and bootable backup.

This script may call the following **steps**, that are itself functions
in the script.

The main part of the script could look like this::

  eval "$ia_init"
  ia_add "opencrypt <-i>"
  ia_add "mountbkup <-i>"
  ia_add "synccopy"
  ia_add "lvcopyvms <-i>
  ia_add "fixcrypttab"
  ia_add "fixfstab"
  ia_add "prepare_chroot"
  ia_add "fixinitrd"
  ia_add "run_grub"
  ia_add "clean_chroot"
  ia_add "umountbkup <-i>"
  ia_add "closecrypt <-i>"
  ia -C

SEE ALSO
========

shellia(1), shellia(3)
