mirror of
https://github.com/koalaman/shellcheck.git
synced 2025-03-12 12:35:25 -07:00
General visual layout with some editorial and addition of --rcfile
parent
17bbd4670e
commit
9686369d81
344
Directive.md
344
Directive.md
@ -1,152 +1,274 @@
|
||||
# ShellCheck Directives
|
||||
- [`shellcheck` directives](#shellcheck-directives)
|
||||
- [Documenting directive use](#documenting-directive-use)
|
||||
- [`.shellcheckrc` file](#shellcheckrc-file)
|
||||
- [Supported directives](#supported-directives)
|
||||
- [disable](#disable)
|
||||
- [enable](#enable)
|
||||
- [external-sources](#external-sources)
|
||||
- [source](#source)
|
||||
- [source-path](#source-path)
|
||||
- [shell](#shell)
|
||||
- [Supported options](#supported-options)
|
||||
- [--rcfile](#--rcfile)
|
||||
- [others](#others)
|
||||
|
||||
Shellcheck directives allow you to control how `shellcheck` works, and take the form of comments in files:
|
||||
## `shellcheck` directives
|
||||
|
||||
```sh
|
||||
hexToAscii() {
|
||||
# shellcheck disable=SC2059
|
||||
printf "\x$1"
|
||||
}
|
||||
```
|
||||
Shellcheck directives allow you to control how `shellcheck` works, and can be added:
|
||||
1. As entries in a [`.shellcheckrc` file](#shellcheckrc-file) in the project's root-, or user's home-, directory:
|
||||
|
||||
or entries in a `.shellcheckrc` in the project root or user's home directory:
|
||||
```sh
|
||||
# Don't suggest [ -n "$VAR" ] over [ ! -z "$VAR" ]
|
||||
disable=SC2236
|
||||
|
||||
```none
|
||||
$ cat ~/.shellcheckrc
|
||||
# Suggest ${VAR} in place of $VAR
|
||||
enable=require-variable-braces
|
||||
```
|
||||
1. and/Or as comments inside individual script files:
|
||||
|
||||
# Don't suggest [ -n "$VAR" ] over [ ! -z "$VAR" ]
|
||||
disable=SC2236
|
||||
```sh
|
||||
hexToAscii() {
|
||||
# shellcheck disable=SC2059
|
||||
printf "\x$1"
|
||||
}
|
||||
```
|
||||
|
||||
# Suggest ${VAR} in place of $VAR
|
||||
enable=require-variable-braces
|
||||
```
|
||||
Directives that replace or are immediately after the shebang apply to the entire script.\
|
||||
Otherwise, they are scoped to the command that follows it. _(including compound commands like function definitions, loops and case statements)_
|
||||
|
||||
## Supported directives
|
||||
- A directive may only be applied to a complete command, and can not be used immediately preceding an `else` block or individual `case` branch:
|
||||
|
||||
### disable
|
||||
Prevent shellcheck from processing one or more warnings:
|
||||
```sh
|
||||
# Directive VALID here, applies to whole `case`
|
||||
case $1 in
|
||||
# Directive INVALID, `-v)` is not a complete command
|
||||
-v)
|
||||
# Directive VALID here, applies to whole `if`
|
||||
if [ "$v" ]
|
||||
then
|
||||
# Directive VALID here, applies to `die ..` command
|
||||
die "Only one -v allowed"
|
||||
# Directive INVALID here, `else` is not a complete command
|
||||
else
|
||||
v=1
|
||||
fi ;;
|
||||
esac
|
||||
```
|
||||
|
||||
```sh
|
||||
# shellcheck disable=code[,code...]
|
||||
statement_where_warning_should_be_disabled
|
||||
```
|
||||
- There is no support for scoping a directive to the first structure of the script.\
|
||||
In these cases, use a dummy command like `true` or `:` and then add the directives, such as:
|
||||
|
||||
A range of errors can also be specified, handy when disbaling things for the entire file.
|
||||
```sh
|
||||
#!/bin/bash
|
||||
# shellcheck disable=SC1000-SC9999
|
||||
```
|
||||
```sh
|
||||
# This directive applies to the entire script
|
||||
# shellcheck disable=2086
|
||||
true
|
||||
|
||||
### enable
|
||||
# This directive only applies to this function
|
||||
# shellcheck disable=2043
|
||||
f() {
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
Enables an [[optional]] check (since 0.7.0).
|
||||
### Documenting directive use
|
||||
|
||||
```sh
|
||||
#!/bin/bash
|
||||
# shellcheck enable=require-variable-braces
|
||||
echo "Hello $USER" # Will suggest ${USER}
|
||||
```
|
||||
It is recommended to add a comment to document why a specific directive was used.
|
||||
|
||||
To see a list of optional checks with examples, run `shellcheck --list-optional`. See [[here|optional]] for more information.
|
||||
- The comment can be added on the preceding line.\
|
||||
_(This is the recommended style for long comments.)_
|
||||
|
||||
### external-sources
|
||||
```sh
|
||||
# this is intentional because of reasons
|
||||
# that are long and need explaining
|
||||
# shellcheck disable=SC1234
|
||||
statement_where_warning_should_be_disabled
|
||||
```
|
||||
|
||||
Set whether or not to follow arbitrary file paths in `source` statements (since 0.8.0).
|
||||
- The comment can also be added at the end of the directive line.\
|
||||
_(This is the recommended style for short comments.)_
|
||||
s
|
||||
```sh
|
||||
# shellcheck disable=SC1234 # this is intentional
|
||||
statement_where_warning_should_be_disabled
|
||||
```
|
||||
|
||||
Use `external-sources=true` in `.shellcheckrc` to let shellcheck access arbitrary files, whether or not they're specified as input. `external-sources=false` disables this, which is the default.
|
||||
### `.shellcheckrc` file
|
||||
|
||||
Individual script files can disable but not enable this option.
|
||||
Unless the `--norc` option is used;
|
||||
- `shellcheck` will look for a file named `.shellcheckrc` or `shellcheckrc` _(note without the dot)_,\
|
||||
in the script's directory and each parent directory of that.\
|
||||
If it is not found there, it will look for it in the user's `HOME` directory (fe. `~/.shellcheckrc`),\
|
||||
followed by the `XDG config` directory.\
|
||||
(usually `~/.config/shellcheckrc` on Unix, or `%APPDATA%/shellcheckrc` on Windows)
|
||||
|
||||
### source
|
||||
Tell ShellCheck where to find a sourced file (since 0.4.0):
|
||||
Only the first-found file will be used.
|
||||
- If found, it will read `key=value` pairs from it and treat them as **_file-wide_ directives**.\
|
||||
Example `.shellcheckrc` looks like:
|
||||
|
||||
```sh
|
||||
# shellcheck source=src/examples/config.sh
|
||||
. "$(locate_config)"
|
||||
```
|
||||
```sh
|
||||
# Look for 'source'd files relative to the checked script,
|
||||
# and also look for absolute paths in /mnt/chroot
|
||||
source-path=SCRIPTDIR
|
||||
source-path=/mnt/chroot
|
||||
|
||||
### source-path
|
||||
# Since 0.9.0, values can be quoted with '' or "" to allow spaces
|
||||
source-path="My Documents/scripts"
|
||||
|
||||
Give ShellCheck a path in which to search for sourced file (since 0.7.0).
|
||||
# Allow opening any 'source'd file, even if not specified as input
|
||||
external-sources=true
|
||||
|
||||
```sh
|
||||
# The script will now look for src/examples/mylib.sh
|
||||
# shellcheck source-path=src/examples
|
||||
. mylib.sh
|
||||
```
|
||||
# Turn on warnings for unquoted variables with safe values
|
||||
enable=quote-safe-variables
|
||||
|
||||
The special value `source-path=SCRIPTDIR` will search in the current script's directory, and it can be used as a relative path like `source-path=SCRIPTDIR/../lib`.
|
||||
# Turn on warnings for unassigned uppercase variables
|
||||
enable=check-unassigned-uppercase
|
||||
|
||||
To support the common pattern of `. "$CONFIGDIR/mylib.sh"`, ShellCheck strips one leading, dynamic section before trying to locate the rest. That means that ShellCheck will look for `config.sh` and `utils.sh` in the same directory as this script when it is being checked:
|
||||
# Allow [ ! -z foo ] instead of suggesting -n
|
||||
disable=SC2236
|
||||
```
|
||||
|
||||
```sh
|
||||
#!/bin/sh
|
||||
# shellcheck source-path=SCRIPTDIR
|
||||
here="$( cd "$( dirname "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )"
|
||||
. "$here/config.sh"
|
||||
. "$here/utils.sh"
|
||||
```
|
||||
- ℹ️Note for **Snap** users:\
|
||||
The Snap sandbox disallows access to hidden files.\
|
||||
Use `shellcheckrc` without the dot instead.
|
||||
- ℹ️Note for **Docker** users:\
|
||||
`shellcheck` will only be able to look for files that
|
||||
are **mounted in the container**, so `~/.shellcheckrc` can not be accessed nor read.
|
||||
|
||||
### shell
|
||||
### Supported directives
|
||||
|
||||
Specify the shell for a script (similar to the shebang, if you for any reason don't want to add one) (since [0.4.5](https://github.com/koalaman/shellcheck/issues/581#issuecomment-249437837)):
|
||||
- [disable](#disable)
|
||||
- [enable](#enable)
|
||||
- [external-sources](#external-sources)
|
||||
- [source](#source)
|
||||
- [source-path](#source-path)
|
||||
- [shell](#shell)
|
||||
|
||||
```sh
|
||||
# shellcheck shell=sh
|
||||
echo foo &> bar
|
||||
```
|
||||
#### disable
|
||||
|
||||
Directives that replace or are immediately after the shebang apply to the entire script. Otherwise, they are scoped to the command that follows it (including compound commands like function definitions, loops and case statements). A directive may only be applied to a complete command, and can not be used immediately preceding an `else` block or individual `case` branch:
|
||||
- **4-digits** _(with or without `SC` prefixed)_\
|
||||
_Prevents `shellcheck` from processing one or more warnings:_
|
||||
|
||||
```sh
|
||||
# Directive VALID here, applies to whole `case`
|
||||
case $1 in
|
||||
# Directive INVALID, `-v)` is not a complete command
|
||||
-v)
|
||||
# Directive VALID here, applies to whole `if`
|
||||
if [ "$v" ]
|
||||
then
|
||||
# Directive VALID here, applies to `die ..` command
|
||||
die "Only one -v allowed"
|
||||
# Directive INVALID here, `else` is not a complete command
|
||||
else
|
||||
v=1
|
||||
fi ;;
|
||||
esac
|
||||
```
|
||||
```sh
|
||||
# shellcheck disable=code[,code...]
|
||||
statement_where_warning_should_be_disabled
|
||||
```
|
||||
|
||||
There is no support for scoping a directive to the first structure of the script. In these cases, use a dummy command `true` or `:` and then add directives, such as
|
||||
- A **range** can also be specified, handy when disabaling multiple warnings/errors for the entire file.
|
||||
|
||||
```sh
|
||||
# This directive applies to the entire script
|
||||
# shellcheck disable=2086
|
||||
true
|
||||
```sh
|
||||
#!...
|
||||
# shellcheck disable=SC1000-SC9999
|
||||
# shellcheck disable=1000-9999
|
||||
```
|
||||
ℹ️Silencing parser errors is purely cosmetic; Any parser error found will still stop `shellsheck` at the point of the error.
|
||||
|
||||
# This directive only applies to this function
|
||||
# shellcheck disable=2043
|
||||
f() {
|
||||
...
|
||||
}
|
||||
```
|
||||
#### enable
|
||||
|
||||
Silencing parser errors is purely cosmetic; any parser error found will still stop ShellCheck at the point of the error.
|
||||
[optional checks]: https://github.com/koalaman/shellcheck/wiki/Optional
|
||||
- **keyphrase**\
|
||||
(since 0.7.0)\
|
||||
_Enables one or more [optional checks]._
|
||||
|
||||
## Documenting directive use
|
||||
```sh
|
||||
#!...
|
||||
# shellcheck enable=require-variable-braces
|
||||
echo "Hello $USER" # Will suggest to change into ${USER}
|
||||
```
|
||||
|
||||
To document why a specific directive was used, it is recommended to add a comment.
|
||||
- To see a list of [optional checks] with examples, run:
|
||||
|
||||
The comment can be added on the preceding line. This is the recommended option for long comments.
|
||||
```console
|
||||
shellcheck --list-optional
|
||||
```
|
||||
|
||||
```sh
|
||||
# this is intentional because of reasons
|
||||
# that are long and need explaining
|
||||
# shellcheck disable=SC1234
|
||||
statement_where_warning_should_be_disabled
|
||||
```
|
||||
#### external-sources
|
||||
|
||||
The comment can also be added at the end of the directive line. This is the recommended option for short comments.
|
||||
- **boolean** (true|false|0|1)\
|
||||
(since v0.8.0)\
|
||||
_Allows or disallows `shellcheck` to include the files pointed-to by the `source` or `.` statements while checking._\
|
||||
`external-sources=false` disables this, which is the default.
|
||||
|
||||
```sh
|
||||
# shellcheck disable=SC1234 # this is intentional
|
||||
statement_where_warning_should_be_disabled
|
||||
```
|
||||
- In `.shellcheckrc` set `external-sources=true` to enable it globally.\
|
||||
_(Individual script files can **disable** but not enable this option.)_
|
||||
|
||||
#### source
|
||||
|
||||
- **single filename** (with or without a leading path)\
|
||||
(since v0.4.0)\
|
||||
_Dictates `shellcheck` where to find the to-be-sourced file._
|
||||
|
||||
```sh
|
||||
# shellcheck source=src/examples/config.sh
|
||||
. "$(locate_config)"
|
||||
```
|
||||
|
||||
- see `SCRIPTDIR` in [source-path](#source-path) (since v0.7.0)?
|
||||
|
||||
```sh
|
||||
# shellcheck source=SCRIPTDIR/examples/config.sh
|
||||
source "${my_SCRIPTDIR}/config.sh"
|
||||
```
|
||||
```sh
|
||||
#!...
|
||||
# shellcheck source-path=SCRIPTDIR/examples
|
||||
...
|
||||
source config.sh
|
||||
```
|
||||
|
||||
|
||||
#### source-path
|
||||
|
||||
- **filepath** (absolute or relative)\
|
||||
(since 0.7.0)\
|
||||
_Informs `shellcheck` where to search for sourced files_.
|
||||
|
||||
```sh
|
||||
# The script will now look for src/examples/mylib.sh
|
||||
# shellcheck source-path=src/examples
|
||||
. mylib.sh
|
||||
```
|
||||
|
||||
- The special value `SCRIPTDIR` will search in the current script's directory, and it can be used as a relative path like `SCRIPTDIR/../lib`.\
|
||||
To support the common pattern of `"${SOME_VAR_NAME}/mylib.sh"`, `shellcheck` strips one leading, dynamic section, before trying to locate the rest.\
|
||||
That means that `shellcheck` will look for `config.sh` and `utils.sh` in the same directory as the script itself when it is being checked in the below example:
|
||||
|
||||
```sh
|
||||
#!...
|
||||
# shellcheck source-path=SCRIPTDIR
|
||||
here="$( cd "$( dirname "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )"
|
||||
. "$here/config.sh"
|
||||
. "$here/utils.sh"
|
||||
```
|
||||
|
||||
#### shell
|
||||
|
||||
- **type of shell** (sh|bash||...)\
|
||||
(since [v0.4.5](https://github.com/koalaman/shellcheck/issues/581#issuecomment-249437837))\
|
||||
_Specifies the shell dialect for a script._
|
||||
|
||||
This is similar to a _shebang_/_hashbang/etc_, if you for any reason don't want to add one.
|
||||
|
||||
```sh
|
||||
# shellcheck shell=sh
|
||||
echo foo &> bar
|
||||
```
|
||||
|
||||
### Supported options
|
||||
|
||||
#### --rcfile
|
||||
|
||||
- **filepath**\
|
||||
(since [v0.10.0](https://github.com/koalaman/shellcheck/pull/2908))\
|
||||
_Dictates `shellcheck` to prefer the specified configuration file, instead of searching for one in the default locations first._
|
||||
|
||||
See [`.shellcheckrc` file](#shellcheckrc-file) for the contents of this file.
|
||||
|
||||
#### others
|
||||
- For a listing of other options not mentioned here, and actually supported by your version of `shellcheck`, try one or both of these commands: 😉
|
||||
|
||||
```console
|
||||
man shellcheck
|
||||
```
|
||||
```console
|
||||
shellcheck --help
|
||||
```
|
Loading…
x
Reference in New Issue
Block a user