% Generated by roxygen2: do not edit by hand
% Please edit documentation in R/cnd-handlers.R
\name{try_fetch}
\alias{try_fetch}
\title{Try an expression with condition handlers}
\usage{
try_fetch(expr, ...)
}
\arguments{
\item{expr}{An R expression.}

\item{...}{<\code{\link[=dyn-dots]{dynamic-dots}}> Named condition
handlers. The names specify the condition class for which a
handler will be called.}
}
\description{
\ifelse{html}{\href{https://lifecycle.r-lib.org/articles/stages.html#experimental}{\figure{lifecycle-experimental.svg}{options: alt='[Experimental]'}}}{\strong{[Experimental]}}

\code{try_fetch()} establishes handlers for conditions of a given class
(\code{"error"}, \code{"warning"}, \code{"message"}, ...). Handlers are functions
that take a condition object as argument and are called when the
corresponding condition class has been signalled.

A condition handler can:
\itemize{
\item \strong{Recover from conditions} with a value. In this case the computation of
\code{expr} is aborted and the recovery value is returned from
\code{try_fetch()}. Error recovery is useful when you don't want
errors to abruptly interrupt your program but resume at the
catching site instead.

\if{html}{\out{<div class="sourceCode">}}\preformatted{# Recover with the value 0
try_fetch(1 + "", error = function(cnd) 0)
}\if{html}{\out{</div>}}
\item \strong{Rethrow conditions}, e.g. using \code{abort(msg, parent = cnd)}.
The \code{parent} argument of \code{\link[=abort]{abort()}}, \code{\link[=warn]{warn()}}, and \code{\link[=inform]{inform()}}
can be used to chain conditions. This is typically done to
add information to low-level errors about the high-level context
in which they occurred.

\if{html}{\out{<div class="sourceCode">}}\preformatted{try_fetch(1 + "", error = function(cnd) abort("Failed.", parent = cnd))

try_fetch(
  1 + "",
  error = function(cnd) \{
    warn("Failed. Returning 1", parent = cnd)
    1L
  \}
)
}\if{html}{\out{</div>}}
\item \strong{Inspect conditions}, for instance to log data about warnings
or errors. In this case, the handler must return the \code{\link[=zap]{zap()}}
sentinel to instruct \code{try_fetch()} to ignore (or zap) that
particular handler. The next matching handler is called if any,
and errors bubble up to the user if no handler remains.

\if{html}{\out{<div class="sourceCode">}}\preformatted{log <- NULL
try_fetch(1 + "", error = function(cnd) \{
  log <<- cnd
  zap()
\})
}\if{html}{\out{</div>}}
}

Whereas \code{tryCatch()} catches conditions (discarding any running
code along the way) and then calls the handler, \code{try_fetch()} first
calls the handler with the condition on top of the currently
running code (fetches it where it stands) and then catches the
return value. This is a subtle difference that has implications
for the debuggability of your functions. See the comparison with
\code{tryCatch()} section below.

Another difference between \code{try_fetch()} and the base equivalent is
that errors are matched across chains, see the \code{parent} argument of
\code{\link[=abort]{abort()}}. This is a useful property that makes \code{try_fetch()}
insensitive to changes of implementation or context of evaluation
that cause a classed error to suddenly get chained to a contextual
error. Note that some chained conditions are not inherited, see the
\code{.inherit} argument of \code{\link[=abort]{abort()}} or \code{\link[=warn]{warn()}}. In particular,
downgraded conditions (e.g. from error to warning or from warning
to message) are not matched across parents.
}
\section{Stack overflows}{


A stack overflow occurs when a program keeps adding to itself until
the stack memory (whose size is very limited unlike heap memory) is
exhausted.

\if{html}{\out{<div class="sourceCode">}}\preformatted{# A function that calls itself indefinitely causes stack overflows
f <- function() f()
f()
#> Error: C stack usage  9525680 is too close to the limit
}\if{html}{\out{</div>}}

Because memory is very limited when these errors happen, it is not
possible to call the handlers on the existing program stack.
Instead, error conditions are first caught by \code{try_fetch()} and only
then error handlers are called. Catching the error interrupts the
program up to the \code{try_fetch()} context, which allows R to reclaim
stack memory.

The practical implication is that error handlers should never
assume that the whole call stack is preserved. For instance a
\code{\link[=trace_back]{trace_back()}} capture might miss frames.

Note that error handlers are only run for stack overflows on R >=
4.2. On older versions of R the handlers are simply not run. This
is because these errors do not inherit from the class
\code{stackOverflowError} before R 4.2. Consider using \code{\link[=tryCatch]{tryCatch()}}
instead with critical error handlers that need to capture all
errors on old versions of R.
}

\section{Comparison with \code{tryCatch()}}{


\code{try_fetch()} generalises \code{tryCatch()} and \code{withCallingHandlers()}
in a single function. It reproduces the behaviour of both calling
and exiting handlers depending on the return value of the handler.
If the handler returns the \code{\link[=zap]{zap()}} sentinel, it is taken as a
calling handler that declines to recover from a condition.
Otherwise, it is taken as an exiting handler which returns a value
from the catching site.

The important difference between \code{tryCatch()} and \code{try_fetch()} is
that the program in \code{expr} is still fully running when an error
handler is called. Because the call stack is preserved, this makes
it possible to capture a full backtrace from within the handler,
e.g. when rethrowing the error with \code{abort(parent = cnd)}.
Technically, \code{try_fetch()} is more similar to (and implemented on
top of) \code{\link[base:conditions]{base::withCallingHandlers()}} than \verb{tryCatch().}
}

