Skip to content

Releases: r-lib/rlang

rlang 1.0.2

04 Mar 18:20
Compare
Choose a tag to compare
  • Backtraces of parent errors are now reused on rethrow. This avoids
    capturing the same backtrace twice and solves consistency problems
    by making sure both errors in a chain have the same backtrace.

  • Fixed backtrace oversimplification when cnd is a base error in
    abort(parent = cnd).

  • Internal errors thrown with abort(.internal = TRUE) now mention
    the name of the package the error should be reported to.

  • Backtraces are now separated from error messages with a --- ruler
    line (#1368).

  • The internal bullet formatting routine now ignores unknown names
    (#1364). This makes it consistent with the cli package, increases
    resilience against hard-to-detect errors, and increases forward
    compatibility.

  • abort() and friends no longer calls non-existent functions
    (e.g. cli::format_error() or cli::format_warning) when the
    installed version of cli is too old (#1367, tidyverse/dplyr#6189).

  • Fixed an OOB subsetting error in abort().

rlang 1.0.1

03 Feb 07:57
Compare
Choose a tag to compare
  • New rlang_call_format_srcrefs global option (#1349). Similar to
    rlang_trace_format_srcrefs, this option allows turning off the
    display of srcrefs in error calls. This can be useful for
    reproducibility but note that srcrefs are already disabled
    within testthat by default.

  • abort(parent = NA) is now supported to indicate an unchained
    rethrow. This helps abort() detect the condition handling context
    to create simpler backtraces where this context is hidden by
    default.

  • When parent is supplied, abort() now loops over callers to
    detect the condition handler frame. This makes it easier to wrap or
    extract condition handlers in functions without supplying .frame.

  • When parent is supplied and call points to the condition setup
    frame (e.g. withCallingHandlers() or try_fetch()), call is
    replaced with the caller of that setup frame. This provides a more
    helpful default call.

  • is_call() is now implemented in C for performance.

  • Fixed performance regression in trace_back().

  • Fixed a partial matching issue with header, body, and footer
    condition fields.

  • eval_tidy() calls are no longer mentioned in error messages.

rlang 1.0.0

27 Jan 09:20
Compare
Choose a tag to compare

Major changes

This release focuses on the rlang errors framework and features
extensive changes to the display of error messages.

  • abort() now displays errors as fully bulleted lists. Error headers
    are displayed with a ! prefix. See
    https://rlang.r-lib.org/reference/topic-condition-customisation.html
    to customise the display of error messages.

  • abort() now displays a full chain of messages when errors are
    chained with the parent argument. Following this change, you
    should update dplyr to version 1.0.8 to get proper error messages.

  • abort() now displays function calls in which a message originated
    by default. We have refrained from showing these calls until now to
    avoid confusing messages when an error is thrown from a helper
    function that isn't relevant to users.

    To help with these cases, abort() now takes a call argument that
    you can set to caller_env() or parent.frame() when used in a
    helper function. The function call corresponding to this environment
    is retrieved and stored in the condition.

  • cli formatting is now supported. Use cli::cli_abort() to get
    advanced formatting of error messages, including indented bulleted
    lists. See https://rlang.r-lib.org/reference/topic-condition-formatting.html.

  • New try_fetch() function for error handling. We recommend to use
    it for chaining errors. It mostly works like tryCatch() with a few
    important differences.

    • Compared to tryCatch(), try_fetch() preserves the call
      stack. This allows full backtrace capture and allows recover()
      to reach the error site.

    • Compared to withCallingHandler(), try_fetch() is able to
      handle stack overflow errors (this requires R 4.2, unreleased at
      the time of writing).

  • The tidy eval documentation has been fully rewritten to reflect
    current practices. Access it through the "Tidy evaluation" and
    "Metaprogramming" menus on https://rlang.r-lib.org.

Breaking changes

  • The .data object exported by rlang now fails when subsetted
    instead of returning NULL. This new error helps you detect when
    .data is used in the wrong context.

    We've noticed several packages failing after this change because
    they were using .data outside of a data-masking context. For
    instance the by argument of dplyr::join() is not data-masked.
    Previously dplyr::join(by = .data$foo) would silently be
    interpreted as dplyr::join(by = NULL). This is now an error.

    Another issue is using .data inside ggplot2::labs(...). This is
    not allowed since labs() isn't data-masked.

  • call_name() now returns NULL instead of "::" for calls of the
    form foo::bar.

    We've noticed some packages do not check for NULL results from
    call_name(). Note that many complex calls such as foo()(),
    foo$bar() don't have a "name" and cause a NULL result. This is
    why you should always check for NULL results when using
    call_name().

    We've added the function is_call_simple() to make it easier to
    work safely with call_name(). The invariant is that call_name()
    always returns a string when is_call_simple() returns TRUE.
    Conversely it always returns NULL when is_call_simple() retuns
    FALSE.

  • is_expression() now returns FALSE for manually constructed
    expressions that can't be created by the parser. It used to return
    TRUE for any calls, including those that contain injected objects.

    Consider using is_call() or just remove the expression check. In
    many cases it is fine letting all objects go through when an
    expression is expected. For instance you can inject objects directly
    inside dplyr arguments:

    x <- seq_len(nrow(data))
    dplyr::mutate(data, col = !!x)
    
  • If a string is supplied to as_function() instead of an object
    (function or formula), the function is looked up in the global
    environment instead of the calling environment. In general, passing
    a function name as a string is brittle. It is easy to forget to pass
    the user environment to as_function() and sometimes there is no
    obvious user environment. The support for strings should be
    considered a convenience for end users only, not for programmers.

    Since environment forwarding is easy to mess up, and since the
    feature is aimed towards end users, as_function() now defaults to
    the global environment. Supply an environment explicitly if that is
    not correct in your case.

  • with_handlers(), call_fn(), and friendly_type() are deprecated.

  • The action argument of check_dots_used(), check_dots_unnamed(),
    and check_dots_empty() is deprecated in favour of the new error
    argument which takes an error handler.

  • Many functions deprecated deprecated in rlang 0.2.0 and 0.3.0 have
    been removed from the package.

Fixes and features

tidyeval

  • New englue() operator to allow string-embracing outside of dynamic
    dots (#1172).

  • New data_sym() and data_syms() functions to create calls of the
    form .data$foo.

  • .data now fails early when it is subsetted outside of a data mask
    context. This provides a more informative error message (#804, #1133).

  • as_label() now better handles calls to infix operators (#956,
    r-lib/testthat#1432). This change improves auto-labelled expressions
    in data-masking functions like tibble(), mutate(), etc.

  • The {{ operator is now detected more strictly (#1087). If
    additional arguments are supplied through {, it is no longer
    interpreted as an injection operator.

  • The .ignore_empty argument of enexprs() and enquos() no longer
    treats named arguments supplied through ... as empty, consistently
    with exprs() and quos() (#1229).

  • Fixed a hang when a quosure inheriting from a data mask is evaluated
    in the mask again.

  • Fixed performance issue when splicing classes that explicitly
    inherit from list with !!! (#1140, r-lib/vctrs#1170).

  • Attributes of quosure lists are no longer modified by side effect
    (#1142).

  • enquo(), enquos() and variants now support numbered dots like
    ..1 (#1137).

  • Fixed a bug in the AST rotation algorithm that caused the !!
    operator to unexpectedly mutate injected objects (#1103).

  • Fixed AST rotation issue with !! involving binary operators (#1125).

rlang errors

  • try_fetch() is a flexible alternative to both tryCatch() and
    withCallingHandlers() (#503). It is also more efficient than
    tryCatch() and creates leaner backtraces.

  • New cnd_inherits() function to detect a class in a chain of errors
    (#1293).

  • New global_entrace() function, a user-friendly helper for
    configuring errors in your RProfile. Call it to enrich all base
    errors and warnings with an rlang backtrace. This enables
    last_error(), last_warnings(), last_messages(), and
    backtrace_on_error support for all conditions.

  • New global_handle() function to install a default configuration of
    error handlers. This currently calls global_entrace() and
    global_prompt_install(). Expect more to come.

  • The "Error:" part of error messages is now printed by rlang instead
    of R. This introduces several cosmetic and informative changes in
    errors thrown by abort():

    • The call field of error messages is now displayed, as is the
      default in base::stop(). The call is only displayed if it is a
      simple expression (e.g. no inlined function) and the arguments are
      not displayed to avoid distracting from the error message. The
      message is formatted with the tidyverse style (code formatting
      by the cli package if available).

    • The source location is displayed (as in base::stop()) if call
      carries a source reference. Source locations are not displayed
      when testthat is running to avoid brittle snapshots.

    • Error headers are always displayed on their own line, with a "!"
      bullet prefix.

    See https://rlang.r-lib.org/reference/topic-condition-customisation.html
    to customise this new display.

  • The display of chained errors created with the parent argument of
    abort() has been improved. Chains of errors are now displayed at
    throw time with the error prefix "Caused by error:".

  • The print() method of rlang errors (commonly invoked with
    last_error()) has been improved:

    • Display calls if present.
    • Chained errors are displayed more clearly.
  • inform() and warn() messages can now be silenced with the global
    options rlib_message_verbosity and rlib_warning_verbosity.

  • abort() now outputs error messages to stdout in interactive
    sessions, following the same approach as inform().

  • Errors, warnings, and messages generated from rlang are now
    formatted with cli. This means in practice that long lines are
    width-wrapped to the terminal size and user themes are applied.
    This is currently only the case for rlang messages.

    This special formatting is not applied when abort(), warn(), and
    inform() are called from another namespace than rlang.
    See https://rlang.r-lib.org/reference/topic-condition-formatting.html
    if you'd like to use cli to format condition messages in your
    package.

  • format_error_bullets() (used as a fallback instead of cli) now
    treats:

    • Unnamed elements as unindented line breaks (#1130)
    • Elements named "v" as green ticks (@rossellhayes)
    • Elements named " " as indented line breaks
    • Elements named "*" as normal bullets
    • Elements named "!" as warning bullets

    For convenience, a fully unnamed vector is interpreted as a vector
    of "*" bullets.

  • abort() gains a .internal argument. When set to TRUE, a footer
    bullet is added to message to let the user know that the error is
    inter...

Read more

rlang 0.4.11

02 May 06:18
Compare
Choose a tag to compare
  • Fix for CRAN checks.

  • Fixed a gcc11 warning related to hash() (#1088).

rlang 0.4.10

04 Jan 09:51
Compare
Choose a tag to compare
  • New hash() function to generate 128-bit hashes for arbitrary R objects
    using the xxHash library. The implementation is modeled after
    xxhashlite, created
    by @coolbutuseless.

  • New check_installed() function. Unlike is_installed(), it asks
    the user whether to install missing packages. If the user accepts,
    the packages are installed with pak::pkg_install() if available,
    or utils::install.packages() otherwise. If the session is non
    interactive or if the user chooses not to install the packages, the
    current evaluation is aborted (#1075).

  • rlang is now licensed as MIT (#1063).

  • Fixed an issue causing extra empty lines in inform() messages with
    .frequency (#1076, @schloerke).

  • expr_deparse() now correctly wraps code using :: and :::
    (#1072, @krlmlr).

rlang 0.4.9

26 Nov 10:59
Compare
Choose a tag to compare

Breaking changes

  • Dropped support for the R 3.2 series.

New features

  • inject() evaluates its argument with !!, !!!, and {{
    support.

  • New enquo0() and enquos0() operators for defusing function
    arguments without automatic injection (unquotation).

  • format_error_bullets() is no longer experimental. The message
    arguments of abort(), warn(), and inform() are automatically
    passed to that function to make it easy to create messages with
    regular, info, and error bullets. See ?format_error_bullets for
    more information.

  • New zap_srcref() function to recursively remove source references
    from functions and calls.

  • A new compat file for the zeallot operator %<-% is now available
    in the rlang repository.

  • New %<~% operator to define a variable lazily.

  • New env_browse() and env_is_browsed() functions. env_browse()
    is equivalent to evaluating browser() within an environment. It
    sets the environment to be persistently browsable (or unsets it if
    value = FALSE is supplied).

  • Functions created from quosures with as_function() now print in a
    more user friendly way.

  • New rlang_print_backtrace C callable for debugging from C
    interpreters (#1059).

Bugfixes and improvements

  • The .data pronoun no longer skips functions (#1061). This solves a
    dplyr issue involving rowwise data frames and list-columns of
    functions (tidyverse/dplyr#5608).

  • as_data_mask() now intialises environments of the correct size to
    improve efficiency (#1048).

  • eval_bare(), eval_tidy() (#961), and with_handlers() (#518)
    now propagate visibility.

  • cnd_signal() now ignores NULL inputs.

  • Fixed bug that prevented splicing a named empty vector with the
    !!! operator (#1045).

  • The exit status of is now preserved in non-interactive sessions when
    entrace() is used as an options(error = ) handler (#1052,
    rstudio/bookdown#920).

  • next and break are now properly deparsed as nullary operators.

rlang 0.4.8

08 Oct 11:35
Compare
Choose a tag to compare
  • Backtraces now include native stacks (e.g. from C code) when the
    winch package is installed and
    rlang_trace_use_winch is set to TRUE (@krlmlr).

  • Compatibility with upcoming testthat 3 and magrittr 2 releases.

  • get_env() now returns the proper environment with primitive
    functions, i.e. the base namespace rather than the base environment
    (r-lib/downlit#32).

  • entrace() no longer handles non-rlang errors that carry a
    backtrace. This improves compatibility with packages like callr.

  • Backtraces of unhandled errors are now displayed without truncation
    in non-interactive sessions (#856).

  • is_interactive() no longer consults "rstudio.notebook.executing"
    option (#1031).

rlang 0.4.7

13 Jul 12:06
Compare
Choose a tag to compare
  • cnd_muffle() now returns FALSE instead of failing if the
    condition is not mufflable (#1022).

  • warn() and inform() gain a .frequency argument to control how
    frequently the warning or message should be displayed.

  • New raw_deparse_str() function for converting a raw vector into a
    string of hexadecimal characters (@krlmlr, #978).

  • The backtraces of chained errors are no longer decomposed by error
    context. Instead, the error messages are displayed as a tree to
    reflect the error ancestry, and the deepest backtrace in the ancestry
    is displayed.

    This change simplifies the display (#851) and makes it possible to
    rethow errors from a calling handler rather than an exiting handler,
    which we now think is more appropriate because it allows users to
    recover() into the error.

  • env_bind(), env_bind_active(), env_bind_lazy(), env_get(),
    and env_get_list() have been rewritten in C.

  • env_poke() now supports zap() sentinels for removing bindings
    (#1012) and has better support for characters that are not
    representable in the local encoding.

  • env_poke() has been rewritten in C for performance.

  • The unicode translation warnings that appeared on Windows with R 4.0
    are now fixed.

  • env_unbind(inherit = TRUE) now only removes a binding from the
    first parent environment that has a binding. It used to remove the
    bindings from the whole ancestry. The new behaviour doesn't
    guarantee that a scope doesn't have a binding but it is safer.

  • env_has() is now rewritten in C for performance.

  • dots_list() gains a .named argument for auto-naming dots (#957).

  • It is now possible to subset the .data pronoun with quosured
    symbols or strings (#807).

  • Expressions like quote(list("a b" = 1)) are now properly deparsed
    by expr_deparse() (#950).

  • parse_exprs() now preserves names (#808). When a single string
    produces multiple expressions, the names may be useful to figure out
    what input produced which expression.

  • parse_exprs() now supports empty expressions (#954).

  • list2(!!!x) no longer evaluates x multiple times (#981).

  • is_installed() now properly handles a pkg argument of length > 1.
    Before this it silently tested the first element of pkg only
    and thus always returned TRUE if the first package was installed
    regardless of the actual length of pkg. (#991, @salim-b)

  • arg_match0() is a faster version of arg_match() for use when performance
    is at a premium (#997, @krlmlr).

rlang 0.4.6

04 May 07:21
Compare
Choose a tag to compare
  • !!! now uses a combination of length(), names(), and [[ to splice
    S3 and S4 objects. This produces more consistent behaviour than as.list()
    on a wider variety of vector classes (#945, tidyverse/dplyr#4931).

rlang 0.4.5

10 Mar 16:55
Compare
Choose a tag to compare
  • set_names(), is_formula(), and names2() are now implemented in
    C for efficiency.

  • The .data pronoun now accepts symbol subscripts (#836).

  • Quosure lists now explicitly inherit from "list". This makes them
    compatible with the vctrs package (#928).

  • All rlang options are now documented in a centralised place, see
    ?rlang::faq-options (#899, @smingerson).

  • Fixed crash when env_bindings_are_lazy() gets improper arguments (#923).

  • arg_match() now detects and suggests possible typos in provided
    arguments (@jonkeane, #798).

  • arg_match() now gives an error if argument is of length greater
    than 1 and doesn't exactly match the values input, similar to base
    match.arg (#914, @AliciaSchep)