Title: | Advanced 'tryCatch()' and 'try()' Functions |
---|---|
Description: | Advanced tryCatch() and try() functions for better error handling (logging, stack trace with source code references and support for post-mortem analysis via dump files). |
Authors: | Juergen Altfeld [aut, cre, cph], Charles Epaillard [ctb], Brandon Bertelsen [ctb], Valerian Wrobel [ctb], Duccio Aiazzi [ctb] |
Maintainer: | Juergen Altfeld <[email protected]> |
License: | GPL-3 | file LICENSE |
Version: | 1.3.2 |
Built: | 2025-02-28 06:02:56 UTC |
Source: | https://github.com/aryoda/trycatchlog |
tryCatchLog
or tryLog
You can get the last logging output by calling last.tryCatchLog.result
.
append.to.last.tryCatchLog.result(new.log.entry)
append.to.last.tryCatchLog.result(new.log.entry)
new.log.entry |
the new log entry (a |
THIS FUNCTION IS USED ONLY PACKAGE INTERNALLY!
the complete logging result of the last call to tryCatchLog
or tryLog
as data.frame
THIS IS A PACKAGE INTERNAL FUNCTION AND THEREFORE NOT EXPORTED.
last.tryCatchLog.result
,
reset.last.tryCatchLog.result
,
data.frame
row containing all relevant logging information in columnsThe serverity level should correspond to the condition class.
build.log.entry( timestamp, severity, msg.text, execution.context.msg, call.stack, dump.file.name, omit.call.stack.items = 0 )
build.log.entry( timestamp, severity, msg.text, execution.context.msg, call.stack, dump.file.name, omit.call.stack.items = 0 )
timestamp |
|
severity |
severity level of the log entry ((ERROR, WARN, INFO etc.) |
msg.text |
Logging message (e. g. error message) |
execution.context.msg |
a text identifier (eg. the PID or a variable value) that will be appended to msg.text for catched conditions. Must be a character or an error is thrown. |
call.stack |
a call stack created by |
dump.file.name |
name of the created dump file (leave empty if the |
omit.call.stack.items |
the number of stack trace items to ignore (= last x calls) in
the passed |
An object of class tryCatchLog.log.entry
and data.frame
and the following columns:
timestamp - creation date and time of the logging entry
severity - the serverity level of the log entry (ERROR, WARN, INFO etc.)
msg.text - the message text of the log entry
compact.stack.trace - the short stack trace containing only entries with source code references down to line of code that has thrown the condition
full.stack.trace - the full stack trace with all calls down to the line of code that has thrown the condition (including calls to R internal functions and other functions even when the source code in not available).
dump.file.name - name of the created dump file (if any)
THIS IS A PACKAGE INTERNAL FUNCTION AND THEREFORE NOT EXPORTED.
last.tryCatchLog.result
build.log.output
To view the formatted output print the logging output in a console use cat
(instead of printing the output with print
which shows the newline escape codes).
build.log.output( log.results, include.full.call.stack = getOption("tryCatchLog.include.full.call.stack", TRUE), include.compact.call.stack = getOption("tryCatchLog.include.compact.call.stack", TRUE), include.severity = TRUE, include.timestamp = FALSE, use.platform.newline = FALSE )
build.log.output( log.results, include.full.call.stack = getOption("tryCatchLog.include.full.call.stack", TRUE), include.compact.call.stack = getOption("tryCatchLog.include.compact.call.stack", TRUE), include.severity = TRUE, include.timestamp = FALSE, use.platform.newline = FALSE )
log.results |
A |
include.full.call.stack |
Flag of type |
include.compact.call.stack |
Flag of type |
include.severity |
|
include.timestamp |
|
use.platform.newline |
|
A ready to use logging output with stack trace
(as character
)
The logged call stack details (compact, full or both) can be configured globally
using the options tryCatchLog.include.full.call.stack
and tryCatchLog.include.compact.call.stack
.
The result of the package internal function build.log.entry
can be passed as log.results
argument.
last.tryCatchLog.result
build.log.entry
CR + LF on Windows, else only LF...
determine.platform.NewLine()
determine.platform.NewLine()
This function is pendant to Microsoft's .Net "Environment.NewLine".
the new line character(s) for the current operating system
THIS IS A PACKAGE INTERNAL FUNCTION AND THEREFORE NOT EXPORTED.
Enriches the current call stack with the source file names and row numbers to track the location of thrown conditions and generates a prettily formatted list of strings
get.pretty.call.stack(call.stack, omit.last.items = 0, compact = FALSE)
get.pretty.call.stack(call.stack, omit.last.items = 0, compact = FALSE)
call.stack |
Call stack object created by |
omit.last.items |
Number of call stack items to drop from the end of the full stack trace |
compact |
TRUE will return only call stack items that have a source code reference (FALSE all) |
How to read the call stack:
Call stack items consist of:<call stack item number> [<file name>#<row number>:] <expression executed by this code line>
The last call stack items with a file name and row number points to the source code line causing the error.
Ignore all call stack items that do not start with a file name and row number (R internal calls only)
You should only call this function from within withCallingHandlers
, NOT from within tryCatch
since tryCatch unwinds the call stack to the tryCatch position and the source of the condition cannot be identified anymore.
The call stack (sys.calls
) without the last number of function calls (given by "omit.last.items")
to remove irrelevant calls caused e. g. by exception handler (withCallingHandlers
)
or restarts (of warnings).
tryCatchLog
, tryLog
, limitedLabelsCompact
The data type is also indicated if an option is set (since a wrong data type may cause problems). If an option is not set "(not set)" is shown as value.
get.pretty.option.value(option.name)
get.pretty.option.value(option.name)
option.name |
Name of the option (as character) |
THIS IS AN INTERNAL PRIVATE FUNCTION OF THE PACKAGE.
The option as key/value string in one line
get.pretty.tryCatchLog.options
## Not run: tryCatchLog:::get.pretty.option.value("warn") # [1] "Option warn = 0 (double)" ## End(Not run)
## Not run: tryCatchLog:::get.pretty.option.value("warn") # [1] "Option warn = 0 (double)" ## End(Not run)
This is a convenience function whose result can be used e. g. to log the current settings.
get.pretty.tryCatchLog.options()
get.pretty.tryCatchLog.options()
If an option is not set the string "(not set)" is shown as value.
The data type is also indicated if an option is set (since a wrong data type may cause problems).
The current option settings as string (one per line as key/value pair), e. g.
Option tryCatchLog.write.error.dump.file = FALSE (logical) Option tryCatchLog.write.error.folder = . (character) Option tryCatchLog.silent.warnings = FALSE (logical) Option tryCatchLog.silent.messages = (not set)
cat(get.pretty.tryCatchLog.options()) # "cat" does apply new line escape characters
cat(get.pretty.tryCatchLog.options()) # "cat" does apply new line escape characters
The log.entry
is checked against the existing log entries from
last.tryCatchLog.result
using the following columns:
msg.text
full.stack.trace
is.duplicated.log.entry(log.entry)
is.duplicated.log.entry(log.entry)
log.entry |
A |
TRUE
if the log.entry
is a duplicate, else FALSE
Required function to fix issue #18 (https://github.com/aryoda/tryCatchLog/issues/18)
last.tryCatchLog.result
,
build.log.entry
Use this function to check for optional package dependencies within this package.
is.package.available(package.name)
is.package.available(package.name)
package.name |
Name of the package (as string) |
This is a package-internal function!
See section ‘Good practice’ in '?.onAttach'.
TRUE
if the packages is installed, otherwise FALSE
(invisible)
http://r-pkgs.had.co.nz/description.html
tryCatchLog:::is.package.available("tryCatchLog") # must be TRUE :-)
tryCatchLog:::is.package.available("tryCatchLog") # must be TRUE :-)
Throws a warning if an indication for Windows OS were found but the Windows OS cannot be recognized for sure (via a second different check).
is.windows()
is.windows()
TRUE
of running on a Windows OS else FALSE
is.windows()
is.windows()
tryCatchLog
or tryLog
This funktion makes the logging results of all thrown conditions of the last tryCatchLog
or tryLog
call
available in a structured form (data.frame
).
last.tryCatchLog.result()
last.tryCatchLog.result()
The typical use case is to get and store the log output not only in a log file but also in another place that is not supported by the logging framework, e. g. in a data base table of your application or displaying it in a GUI (user interface).
Another use case is to review the last log output on the console during debugging.
the logging result of the last call to tryCatchLog
or tryLog
as data.frame
comprised of one row per logged condition with these columns:
timestamp - creation date and time of the logging entry
severity - the serverity level of the log entry (ERROR, WARN, INFO etc.)
msg.text - the message text of the log entry
execution.context.msg - text identifier (eg. the PID or a variable value)
as passed as argument to tryCatchLog
or tryLog
to make it easier to identify the runtime state that caused
a condition esp. in parallel execution scenarios
compact.stack.trace - the short stack trace containing only entries with source code references down to line of code that has thrown the condition
full.stack.trace - the full stack trace with all calls down to the line of code that has thrown the condition (including calls to R internal functions and other functions even when the source code in not available).
dump.file.name - name of the created dump file (if any)
If no condition is logged at all an empty data.table
is returned.
last.tryCatchLog.result()
last.tryCatchLog.result()
Converts a call stack into a list of printable strings ("labels") with a limited length per call.
If source code references are available they are also printed in the stack trace using this notation:
<file name>#<line number>: executed R expression (call)
limitedLabelsCompact( value, compact = FALSE, maxwidth = getOption("width") - 5L )
limitedLabelsCompact( value, compact = FALSE, maxwidth = getOption("width") - 5L )
value |
a list of calls ("call.stack") generated by |
compact |
if TRUE only calls that contain a source code reference (attribute "srcref") are returned (plus always the first call); if FALSE all calls will be returned. |
maxwidth |
Maximum number of characters per call in the return value (longer strings will be cutted). Must be between 40 and 2000 (until version 1.2.2: 1000) |
By default the maximum number of source code rows that are printed per call in the full stack trace
is 10. You can change this via the option tryCatchLog.max.lines.per.call
(see example).
R does track source code references only if you set the option "keep.source" to TRUE via
options(keep.source = TRUE)
. Without this option this function cannot enrich source code references.
If you use Rscript
to start a non-interactive R script as batch job you
have to set this option since it is FALSE by default. You can add this option to your
.Rprofile file or use a startup R script that sets this option and sources your
actual R script then.
This function is based on the undocumented limitedLabels
function of the base package.
The source code can be viewed by entering limitedLabels
in the R console.
The attributes required to add source file names and line numbers to the calls (srcref and srcfile)
and how they are created internally are explained in this article:
https://journal.r-project.org/archive/2010-2/RJournal_2010-2_Murdoch.pdf
A list of strings (one for each call).
If compact
is TRUE
at the last call is returned even if it does not contain
a source code reference.
sys.calls
, tryCatchLog
, get.pretty.call.stack
options(tryCatchLog.max.lines.per.call = 30) limitedLabelsCompact(sys.calls(), TRUE)
options(tryCatchLog.max.lines.per.call = 30) limitedLabelsCompact(sys.calls(), TRUE)
This is a package-internal function.
log2console(severity.level, msg)
log2console(severity.level, msg)
severity.level |
String containing the severity level
( |
msg |
The message to be printed (as character). |
The log message as it was printed to the console.
NA
is printed as empty string.
tryCatchLog:::log2console("WARN", "this is my last warning")
tryCatchLog:::log2console("WARN", "this is my last warning")
CR + LF on Windows, else only LF...
platform.NewLine()
platform.NewLine()
The newline character(s) are determined once at package loading time.
the new line character(s) for the current operating system
platform.NewLine()
platform.NewLine()
tryCatchLog
or tryLog
to an empty listYou can get the last logging output by calling last.tryCatchLog.result
.
reset.last.tryCatchLog.result()
reset.last.tryCatchLog.result()
invisible: TRUE
THIS IS A PACKAGE INTERNAL FUNCTION AND THEREFORE NOT EXPORTED.
last.tryCatchLog.result
,
append.to.last.tryCatchLog.result
,
tryCatchLog
for the different severity levelsThe logging functions must have at least one parameter: The logging message (as character) which must be the first argument.
set.logging.functions( error.log.func = function(msg) tryCatchLog:::log2console("ERROR", msg), warn.log.func = function(msg) tryCatchLog:::log2console("WARN", msg), info.log.func = function(msg) tryCatchLog:::log2console("INFO", msg), logger.package.name = "tryCatchLog" )
set.logging.functions( error.log.func = function(msg) tryCatchLog:::log2console("ERROR", msg), warn.log.func = function(msg) tryCatchLog:::log2console("WARN", msg), info.log.func = function(msg) tryCatchLog:::log2console("INFO", msg), logger.package.name = "tryCatchLog" )
error.log.func |
The logging function for errors |
warn.log.func |
The logging function for warning |
info.log.func |
The error function for messages |
logger.package.name |
The logging package name of the functions (just internally used to print the name). For self-made logging functions (not part of a package) should use "custom functions" but can use any other name (it has no functionality). |
The default logging functions are internal functions without any dependencies to other logging packages. They use the same logging output format as futile.logger version 1.4.3.
If you want to disable any logging output you should use a decent logging framework
which allows to set the logging threshold (e. g. futile.logger's flog.threshold
).
The package-internal default logging functions are only a minimal implementation and are not meant to replace a decent logging framework.
To activate another logging package that is supported by tryCatchLog
use set.logging.package
.
Nothing
tryCatchLog
set.logging.package
# To disable any logging you could use "empty" functions set.logging.functions( error.log.func = function(msg) invisible(), warn.log.func = function(msg) invisible(), info.log.func = function(msg) invisible())
# To disable any logging you could use "empty" functions set.logging.functions( error.log.func = function(msg) invisible(), warn.log.func = function(msg) invisible(), info.log.func = function(msg) invisible())
If this optional argument is omitted, either the package name
from the option tryCatchLog.preferred.logging.package
is enabled
or all supported logging packages (see the vector of default values) are probed in this order
and the first existing (= installed) logging package is enabled.
set.logging.package( logging.package.name = getOption("tryCatchLog.preferred.logging.package", c("futile.logger", "lgr", "tryCatchLog")) )
set.logging.package( logging.package.name = getOption("tryCatchLog.preferred.logging.package", c("futile.logger", "lgr", "tryCatchLog")) )
logging.package.name |
The name of the logging package (character) that shall be enabled. |
If the passed logging framework(s) is/are not installed the internal logging functions of
tryCatchLog
will be enabled as fall-back.
To enable a non-supported logging framework you can call set.logging.functions
instead.
To configure a standard logging package when tryCatchLog
is loaded and set.logging.package
is called without an argument
you can use the option tryCatchLog.preferred.logging.package
.
You could also set a vector of packages to "probe" (the first installed package of the list is taken,
in none is installed tryCatchLog
-internal logging is used.
The name of the enabled logging framework
tryCatchLog:::set.logging.package("futile.logger") tryCatchLog:::set.logging.package("lgr") tryCatchLog:::set.logging.package("tryCatchLog") # takes the first installed logging package from the list of supported packages tryCatchLog:::set.logging.package() # only considered when tryCatchLog is loaded or set.logging.package() is called! # takes the logging package fromt the configured option (if installed, else tryCatchLog) options(tryCatchLog.preferred.logging.package = "futile.logger") tryCatchLog:::set.logging.package()
tryCatchLog:::set.logging.package("futile.logger") tryCatchLog:::set.logging.package("lgr") tryCatchLog:::set.logging.package("tryCatchLog") # takes the first installed logging package from the list of supported packages tryCatchLog:::set.logging.package() # only considered when tryCatchLog is loaded or set.logging.package() is called! # takes the logging package fromt the configured option (if installed, else tryCatchLog) options(tryCatchLog.preferred.logging.package = "futile.logger") tryCatchLog:::set.logging.package()
This function evaluates an expression passed in the expr
parameter,
logs all conditions and executes the condition handlers passed in ...
(if any).
tryCatchLog( expr, ..., execution.context.msg = "", finally = NULL, write.error.dump.file = getOption("tryCatchLog.write.error.dump.file", FALSE), write.error.dump.folder = getOption("tryCatchLog.write.error.dump.folder", "."), silent.warnings = getOption("tryCatchLog.silent.warnings", FALSE), silent.messages = getOption("tryCatchLog.silent.messages", FALSE), include.full.call.stack = getOption("tryCatchLog.include.full.call.stack", TRUE), include.compact.call.stack = getOption("tryCatchLog.include.compact.call.stack", TRUE), logged.conditions = getOption("tryCatchLog.logged.conditions", NULL) )
tryCatchLog( expr, ..., execution.context.msg = "", finally = NULL, write.error.dump.file = getOption("tryCatchLog.write.error.dump.file", FALSE), write.error.dump.folder = getOption("tryCatchLog.write.error.dump.folder", "."), silent.warnings = getOption("tryCatchLog.silent.warnings", FALSE), silent.messages = getOption("tryCatchLog.silent.messages", FALSE), include.full.call.stack = getOption("tryCatchLog.include.full.call.stack", TRUE), include.compact.call.stack = getOption("tryCatchLog.include.compact.call.stack", TRUE), logged.conditions = getOption("tryCatchLog.logged.conditions", NULL) )
expr |
R expression to be evaluated |
... |
condition handler functions (as in |
execution.context.msg |
a text identifier (eg. the PID or a variable value) that will be added to msg.text
for catched conditions. This makes it easier to identify the runtime state that caused
a condition esp. in parallel execution scenarios.
The value must be of length 1 and will be coerced to character.
Expressions are not allowed.
The added output has the form: |
finally |
expression to be evaluated at the end (after executing the expressiond and calling the matching handler). |
write.error.dump.file |
|
write.error.dump.folder |
|
silent.warnings |
|
silent.messages |
|
include.full.call.stack |
Flag of type |
include.compact.call.stack |
Flag of type |
logged.conditions |
|
The finally
expression is then always evaluated at the end.
Condition handlers work as in base R's tryCatch
.
Conditions are also logged including the function call stack with file names and line numbers (if available).
By default the maximum number of source code rows that are printed per call in the full stack trace
is 10. You can change this via the option tryCatchLog.max.lines.per.call
(see example).
This function shall overcome some drawbacks of the standard tryCatch
function.
For more details see https://github.com/aryoda/tryCatchLog.
If the package futile.logger is installed it will be used for writing logging output, otherwise an internal basic logging output function is used.
Before you call tryCatchLog
for the first time you should initialize
the logging framework you are using (e. g.futile.logger to control
the log output (log to console or file etc.):
library(futile.logger) flog.appender(appender.file("my_app.log")) flog.threshold(INFO) # TRACE, DEBUG, INFO, WARN, ERROR, FATAL
If you are using the futile.logger package tryCatchLog
calls
these log functions for the different R conditions to log them:
error -> flog.error
warning -> flog.warn
message -> flog.info
interrupt -> flog.info
'tryCatchLog' does log all conditions (incl. user-defined conditions).
Since the interrupt condition does not have an error message attribute tryCatchLog
uses "User-requested interrupt" as message in the logs.
The log contains the call stack with the file names and line numbers (if available).
R does track source code references of scripts only if you set the option keep.source
to TRUE via
options(keep.source = TRUE)
. Without this option this function cannot enrich source code references.
If you use Rscript
to start a non-interactive R script as batch job you
have to set this option since it is FALSE by default. You can add this option to your
.Rprofile file or use a startup R script that sets this option and sources your
actual R script then.
By default, most packages are built without source reference information.
Setting the environment variable R_KEEP_PKG_SOURCE=yes
before installing a source package
will tell R to keep the source references. You can also use options(keep.source.pkgs = TRUE)
before you install a package.
Setting the parameter tryCatchLog.write.error.dump.file
to TRUE allows a post-mortem analysis of the program state
that led to the error. The dump contains the workspace and in the variable "last.dump"
the call stack (sys.frames
). This feature is very helpful for non-interactive R scripts ("batches").
Setting the parameter tryCatchLog.write.error.dump.folder
to a specific path allows to save the dump in a specific folder.
If not set, the dump will be saved in the working directory.
To start a post-mortem analysis after an error open a new R session and enter:
load("dump_20161016_164050.rda") # replace the dump file name with your real file name
debugger(last.dump)
Note that the dump does not contain the loaded packages when the dump file was created and a dump loaded into memory does therefore not use exactly the same search path. This means:
the program state is not exactly reproducible if objects are stored within a package namespace
you cannot step through your source code in a reproducible way after loading the image if your source code calls functions of non-default packages
the value of the expression passed in as parameter "expr"
To avoid that too many dump files filling your disk space you should omit the write.error.dump.file
parameter and instead set its default value using the option tryCatchLog.write.error.dump.file
in your
.Rprofile file instead (or in a startup R script that sources your actual script).
In case of an error (that you can reproduce) you set the option to TRUE
and re-run your script.
Then you are able to examine the program state that led to the error by debugging the saved dump file.
To see the source code references (source file names and line numbers) in the stack traces you must
set this option before executing your code:options(keep.source = TRUE)
You can execute your code as batch with Rscript
using this shell script command:Rscript -e "options(keep.source = TRUE); source('my_main_function.R')"
http://adv-r.had.co.nz/beyond-exception-handling.html
https://stackoverflow.com/questions/39964040/r-catch-errors-and-continue-execution-after-logging-the-stacktrace-no-tracebac
tryLog
, limitedLabels
, get.pretty.call.stack
,
last.tryCatchLog.result
, set.logging.functions
,
tryCatch
, withCallingHandlers
, signalCondition
,
getOption
tryCatchLog(log(-1)) # logs a warning (logarithm of a negative number is not possible) tryLog(log(-1), execution.context.msg = Sys.getpid()) # set and unset an option options("tryCatchLog.write.error.dump.folder" = "my_log") options("tryCatchLog.write.error.dump.folder" = NULL) options(tryCatchLog.max.lines.per.call = 30) ## Not run: # Use case for "execution.context.msg" argument: Loops and parallel execution library(foreach) # support parallel execution (requires an parallel execution plan) options(tryCatchLog.include.full.call.stack = FALSE) # reduce the ouput for demo purposes res <- foreach(i = 1:12) %dopar% { tryCatchLog(log(10 - i), execution.context.msg = i) } ## End(Not run)
tryCatchLog(log(-1)) # logs a warning (logarithm of a negative number is not possible) tryLog(log(-1), execution.context.msg = Sys.getpid()) # set and unset an option options("tryCatchLog.write.error.dump.folder" = "my_log") options("tryCatchLog.write.error.dump.folder" = NULL) options(tryCatchLog.max.lines.per.call = 30) ## Not run: # Use case for "execution.context.msg" argument: Loops and parallel execution library(foreach) # support parallel execution (requires an parallel execution plan) options(tryCatchLog.include.full.call.stack = FALSE) # reduce the ouput for demo purposes res <- foreach(i = 1:12) %dopar% { tryCatchLog(log(10 - i), execution.context.msg = i) } ## End(Not run)
tryLog
is implemented by calling tryCatchLog
and traps any errors that occur during the evaluation of an expression without stopping the execution
of the script (similar to try
). Errors, warnings and messages are logged.
In contrast to tryCatchLog
it returns but does not stop in case of an error and therefore does
not have the error
and finally
parameters to pass in custom handler functions.
tryLog( expr, write.error.dump.file = getOption("tryCatchLog.write.error.dump.file", FALSE), write.error.dump.folder = getOption("tryCatchLog.write.error.dump.folder", "."), silent.warnings = getOption("tryCatchLog.silent.warnings", FALSE), silent.messages = getOption("tryCatchLog.silent.messages", FALSE), include.full.call.stack = getOption("tryCatchLog.include.full.call.stack", TRUE), include.compact.call.stack = getOption("tryCatchLog.include.compact.call.stack", TRUE), logged.conditions = getOption("tryCatchLog.logged.conditions", NULL), execution.context.msg = "" )
tryLog( expr, write.error.dump.file = getOption("tryCatchLog.write.error.dump.file", FALSE), write.error.dump.folder = getOption("tryCatchLog.write.error.dump.folder", "."), silent.warnings = getOption("tryCatchLog.silent.warnings", FALSE), silent.messages = getOption("tryCatchLog.silent.messages", FALSE), include.full.call.stack = getOption("tryCatchLog.include.full.call.stack", TRUE), include.compact.call.stack = getOption("tryCatchLog.include.compact.call.stack", TRUE), logged.conditions = getOption("tryCatchLog.logged.conditions", NULL), execution.context.msg = "" )
expr |
R expression to be evaluated |
write.error.dump.file |
|
write.error.dump.folder |
|
silent.warnings |
|
silent.messages |
|
include.full.call.stack |
Flag of type |
include.compact.call.stack |
Flag of type |
logged.conditions |
|
execution.context.msg |
a text identifier (eg. the PID or a variable value) that will be added to msg.text
for catched conditions. This makes it easier to identify the runtime state that caused
a condition esp. in parallel execution scenarios.
The value must be of length 1 and will be coerced to character.
Expressions are not allowed.
The added output has the form: |
tryLog
is implemented using tryCatchLog
. If you need need more flexibility for
catching and handling errors use the latter.
Error messages are never printed to the stderr
connection but logged only.
The value of the expression (if expr
is evaluated without an error.
In case of an error: An invisible object of the class "try-error"
containing the error message
and error condition as the "condition"
attribute.
tryCatchLog
,
last.tryCatchLog.result
tryLog(log(-1)) # logs a warning (logarithm of a negative number is not possible) tryLog(log("a")) # logs an error tryCatchLog(log(-1), execution.context.msg = Sys.getpid())
tryLog(log(-1)) # logs a warning (logarithm of a negative number is not possible) tryLog(log("a")) # logs an error tryCatchLog(log(-1), execution.context.msg = Sys.getpid())