Lustre Script Coding Style: Difference between revisions
Jump to navigation
Jump to search
m (→Bash Style: remove duplicate text) |
m (→Functions) |
||
Line 45: | Line 45: | ||
</nowiki> | </nowiki> | ||
* Function arguments should be given local variable names for clarity like "<code>local facet=$1</code>", rather than being used as <code>$1</code> in the function | * Function arguments should be given local variable names for clarity like "<code>local facet=$1</code>", rather than being used as <code>$1</code> in the function | ||
* Use <code>sleep 0.1</code> instead of <code>usleep 100000</code>, since <code>usleep</code> is RHEL-specific | |||
=== Tests and Libraries === | === Tests and Libraries === | ||
* To avoid clustering a single <code>test-framework.sh</code> file, there should be a <code><nowiki><test-lib>.sh</nowiki></code> file for each test that contains specific functions and variables for that test. | * To avoid clustering a single <code>test-framework.sh</code> file, there should be a <code><nowiki><test-lib>.sh</nowiki></code> file for each test that contains specific functions and variables for that test. |
Revision as of 14:00, 18 June 2020
Bash Style
- Bash is a programming language. It includes functions. Shell code outside of functions is effectively code in an implicit main() function. An entire function should be fully seen on one page (~70-90 lines) and be readily comprehensible. If you have any doubts, then it is too complicated. Make it easier to understand by separating it into subroutines.
- The total length of a line (including comment) must not exceed 80 characters. Take advantage of bash's
+=
operator for constants or linefeed escapes\
. - Lines can be split without the need for a linefeed escape after
|
,||
,&
and&&
operators. - The indentation must use 8-column tabs and not spaces. For line continuation, an additional tab should be used to indent the continued line, or align after
[
or(
for continued logic operations. - Comments are just as important in a shell script as in C code.
- Use
$(...)
instead of`...`
for subshell commands, since the former is easier to see the start and end of the subshell command, avoids confusion with'...'
and a small font, and$(...)
can be nested. Use the subshell syntax only when you have to (e.g. when you need to capture the output of a separate program). Using the construct with functions leads to stray output and/or convoluted code struggling to avoid output pollution. It is also more computationally efficient to not fork() the Bash process. Bash is slow enough already. - Use "here string" like
function <<<$var
instead ofecho $var | function
to avoid forking a subshell and pipe - Use built-in Bash Parameter Expansion for variable/string manipulation rather than forking sed/tr if possible.
- Avoid use of "
grep foo | awk '{ print $2 }'
" since "awk '/foo/ { print $2 }'
works just as well and avoids a separate fork + pipe - If a variable is intended to be used as a boolean, then it must be assigned as followed:
local mybool=false # or true if $mybool; then do_stuff fi
- for loops it is possible to avoid a subshell for
$(seq 10)
using the built-in iterator for fixed-length loops (unfortunately,{1..$var}
does not work):
for i in {1..10}; do something_with $i done
- Use
export FOOBAR=val
instead ofFOOBAR=val; export FOOBAR
for clarity and simplicity - Use
[[ expr ]]
instead of[ expr ]
, especially since the[[
test understands regular expression matching with the=~
operator. The easiest way to use it is by putting the RE in a variable and expanding the RE after the operator without quotes. - Use
$((...))
for arithmetic expressions instead ofexpr
Test Framework
Variables
- Names of variables local to current script which are not exported to the environment should be declared with "
local
" and use lowercase letters - Names of global variables or variables that exported to the environment should be UPPERCASE letters
Functions
- Each function must have a section describing what it does and explain the list of parameters
# One line description of this function's purpose # # More detailed description of what the function is doing if necessary # # usage: function_name [--option argument] {required_argument} ... # option: meaning of "option" and its argument # required_argument: meaning of "required_argument" # # expected output and/or return value(s)
- Function arguments should be given local variable names for clarity like "
local facet=$1
", rather than being used as$1
in the function - Use
sleep 0.1
instead ofusleep 100000
, sinceusleep
is RHEL-specific
Tests and Libraries
- To avoid clustering a single
test-framework.sh
file, there should be a<test-lib>.sh
file for each test that contains specific functions and variables for that test. - Any functions, variables that global to all tests should be put in
test-framework.sh
- A test file only need to source
test-framework.sh
and necessary<test-lib>.sh
file