How do I manage log verbosity inside a shell script?
You already have what seems to be the cleanest idea in your question (a wrapper function), but you seem to think it would be messy. I would suggest you reconsider. It could look like the following (not necessarily a full-fledged solution, just to give you the basic idea) :
#!/bin/bash
# Argument 1 : Logging level for that command
# Arguments 2... : Command to execute
# Output suppressed if command level >= current logging level
log()
{
if
(($1 >= logging_level))
then
"${@:2}" >/dev/null 2>&1
else
"${@:2}"
fi
}
logging_level=2
log 1 command1 and its args
log 2 command2 and its args
log 3 command4 and its args
You can arrange for any required redirection (with file descriptors if you want) to be handled in the wrapper function, so that the rest of the script remains readable and free from redirections and conditions depending on the selected logging level.
Elegant way for verbose mode in scripts?
As you noticed, you can define some log
functions like log
, log_debug
, log_error
, etc.
function log () {
if [[ $_V -eq 1 ]]; then
echo "$@"
fi
}
It can help increasing your main code readability and hide show\nonshow logic into logging function.
log "some text"
If _V
(global variable) is equal 1
"some text" will be printed, in other case it will not.
Simple logging levels in Bash
One way to approach this is to create an associative array of all the levels. Each level is assigned a number and those numbers are then compared to decide whether you should log or not. Imagine you wanted to add another logging level. Those if
statements of yours would get out of control:
#!/usr/bin/env bash
declare -A levels=([DEBUG]=0 [INFO]=1 [WARN]=2 [ERROR]=3)
script_logging_level="INFO"
logThis() {
local log_message=$1
local log_priority=$2
#check if level exists
[[ ${levels[$log_priority]} ]] || return 1
#check if level is enough
(( ${levels[$log_priority]} < ${levels[$script_logging_level]} )) && return 2
#log here
echo "${log_priority} : ${log_message}"
}
logThis "This will log" "WARN"
logThis "This will not log" "DEBUG"
logThis "This will not log" "OUCH"
LOG_PRIORITY_SUPPORTED=false
is an example why you should use local
variables in functions. Also, you shouldn't use uppercase variables as they could clash with environmental or internal shell variables.
Check current bash verbosity
if [[ $- =~ v ]]; then
echo "verbose enabled"
else
echo "verbose disabled"
fi
$-
: Contains the current set of enabled options. See:help set
How to echo shell commands as they are executed
set -x
or set -o xtrace
expands variables and prints a little + sign before the line.
set -v
or set -o verbose
does not expand the variables before printing.
Use set +x
and set +v
to turn off the above settings.
On the first line of the script, one can put #!/bin/sh -x
(or -v
) to have the same effect as set -x
(or -v
) later in the script.
The above also works with /bin/sh
.
See the bash-hackers' wiki on set
attributes, and on debugging.
$ cat shl
#!/bin/bash
DIR=/tmp/so
ls $DIR
$ bash -x shl
+ DIR=/tmp/so
+ ls /tmp/so
$
linux bash script log output
Thats because, only error from your gzip execution goes into file. To get what you want, use -
mysqldump -u root -p$Pass --all-databases 2>file.log | gzip > fulldbdmp-$(date +%m%d%Y).dump.gz
How to log every single command executed from shell script
I am aware that you were asking for Bash and Shell scripting and tagged your question accordingly, but in respect to your requirements
- Record every single command that is executed by any user on the system
- Users are unaware that they are being monitored
- A solution something at system level
I am under the assumption that you are looking for Audit Logging.
So you may take advantage from articles like
- Log all commands run by Admins on production servers
- Log every command executed by a User
How to write Bash Script output to chef-client run
If you're passing a specific verbosity level to knife, it will pass the debug flag to chef client on a bootstrap. Looking at knife's docs, there's:
-V, --verbose: More verbose output. Use twice for max verbosity.
Have you tried passing -VV to knife bootstrap
? It should make verbosity = 2, which should trigger passing the debug flag to chef-client during a bootstrap.
For what it's worth, Chef also copies the verbosity setting into Mixlib::CLI's settings. Thus, when you use a bash or execute resource, you should see the output of your bash script within the debug output.
Hope this helps!
Related Topics
How to Capitalize First Letter of Each Line in Bash
How to Find the Particular Text Stored in the File "Data.Txt" and It Occurs Only Once
Bash Completion for Path in Argument (With Equals Sign Present)
Switching Users Using Winscp Between Different Accounts
How to Replace a Multi Line String in a Bunch Files
What Does It Take to Be Durable on Linux
How to Install Poppler for Python 3 in Linux
Kubernetes Can't Start Due to Too Many Open Files in System
Shell Script for Process Monitoring
Sed Error:Bad Option in Substitution Expression
Configure Options for Building Mingw-64 on Linux-64 for Linux-64 (Ultimately Targetting Windows-64)
Catching a Direct Redirect to /Dev/Tty
What Happened to Socket If Network Has Broken Down
Identifying the Preferred Ipv6 Source Address for an Adapter
Perl: What Does Checkstack.Pl in Linux Source Do
How to Install a Node.Js Server at Chat.Mydomain.Com on a Hostgator Vps Hosting