Skip to content

Trying to reassign a reactiveVal to the name of an existing reactiveVal doesn't overwrite the latter #4432

Description

@BajczA475

System details

R version 4.6.1 (2026-06-24 ucrt)
Platform: x86_64-w64-mingw32/x64
Running under: Windows 11 x64 (build 26200)

Matrix products: default
  LAPACK version 3.12.1

locale:
[1] LC_COLLATE=English_United States.utf8  LC_CTYPE=English_United States.utf8    LC_MONETARY=English_United States.utf8
[4] LC_NUMERIC=C                           LC_TIME=English_United States.utf8    

time zone: America/Chicago
tzcode source: internal

attached base packages:
[1] stats     graphics  grDevices utils     datasets  methods   base     

other attached packages:
 [1] ggplotplus_0.5.7      shinyvalidate_0.1.3   patchwork_1.3.2       tibble_3.3.1          DT_0.34.0             ggraph_2.2.2         
 [7] ggplot2_4.0.3         igraph_2.3.3          data.table_1.18.4     scales_1.4.0          Matrix_1.7-5          shinyWidgets_0.9.1   
[13] shinydisconnect_0.1.1 waiter_0.2.5.1        shinyjs_2.1.1         stringr_1.6.0         tidyr_1.3.2           dplyr_1.2.1          
[19] shiny_1.14.0         

loaded via a namespace (and not attached):
 [1] gtable_0.3.6       httr2_1.3.0        bslib_0.12.0       htmlwidgets_1.6.4  ggrepel_0.9.8      lattice_0.22-9    
 [7] vctrs_0.7.3        tools_4.6.1        crosstalk_1.2.2    generics_0.1.4     curl_7.1.0         pkgconfig_2.0.3   
[13] checkmate_2.3.4    RColorBrewer_1.1-3 S7_0.2.2           lifecycle_1.0.5    compiler_4.6.1     farver_2.1.2      
[19] textshaping_1.0.5  ggforce_0.5.0      graphlayouts_1.2.5 httpuv_1.6.17      htmltools_0.5.9    sass_0.4.10       
[25] yaml_2.3.12        later_1.4.8        pillar_1.11.1      jquerylib_0.1.4    MASS_7.3-65        openssl_2.4.2     
[31] rsconnect_1.10.1   cachem_1.1.0       viridis_0.6.5      mime_0.13          tidyselect_1.2.1   digest_0.6.39     
[37] stringi_1.8.9      purrr_1.2.2        labeling_0.4.3     polyclip_1.10-7    fastmap_1.2.0      grid_4.6.1        
[43] cli_3.6.6          magrittr_2.0.5     tidygraph_1.3.1    withr_3.0.3        promises_1.5.0     backports_1.5.1   
[49] otel_0.2.0         gridExtra_2.3.1    askpass_1.2.1      ragg_1.5.2         memoise_2.0.1      viridisLite_0.4.3 
[55] rlang_1.3.0        Rcpp_1.1.2         xtable_1.8-8       glue_1.8.1         tweenr_2.0.3       pkgload_1.5.3     
[61] rstudioapi_0.19.0  jsonlite_2.0.0     R6_2.6.1           systemfonts_1.3.2 

Example application or steps to reproduce the problem

library(shiny)

ui <- fluidPage(
  actionButton("reset", "Recreate x")
)

server <- function(input, output, session) {
  x <- reactiveVal(0)

  observe({
    cat("Observer saw:", x(), "\n")
  })

  observeEvent(input$reset, {
    x <<- reactiveVal(0)  # Rebind x to a new reactiveVal
    x(1)                  # Update the new reactiveVal
  })
}

shinyApp(ui, server)

Describe the problem in detail

I don't think this is actually a bug; I think it's the code working as intended. However, I found it unintuitive enough to warrant a mention in the help docs for reactiveVal().

Basically, in "plain R," if you ran x = 15 and then later ran x = 12, you'd overwrite the original object with the new one. However, if you try this with reactiveVal()s, the same doesn't hold true. It seems like instead of overwriting the original, it creates a new one with the same name, creating a second version that observers and other entities could seemingly point at. Perhaps this has something to do with how assignment works in JS versus in R? I dunno.

However, it means that if I am trying to code, say, a reset button, and I try to reset a reactiveVal by essentially just re-running the same command I used to create it, that won't "reset it," but it also won't error, and observers may still find the un-updated reactiveVal and access it instead, so it creates "silent failure states."

It's obvious, in retrospect, that I need to use the reactiveVal as a function to reset it once it's made, but it wasn't obvious before. Just a note in the Details that says something to the effect of "Assigning a reactiveVal to the name of an existing reactiveVal will not overwrite the latter entity; use the reactiveVal as a function to set or reset its value" would have been instructive for me!

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Priority: LowLow-impact bug, docs polish, papercut, or unclear low-severity request.ai-triage:doneMarks an issue whose AI triage workflow is complete.

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions