Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Investigate freeze/thaw behavior inconsistencies #1791

Open
jcheng5 opened this issue Jul 13, 2017 · 3 comments
Open

Investigate freeze/thaw behavior inconsistencies #1791

jcheng5 opened this issue Jul 13, 2017 · 3 comments

Comments

@jcheng5
Copy link
Member

jcheng5 commented Jul 13, 2017

  1. reactiveVal thaws on onFlushed, reactiveValues... doesn't?
  2. reactiveVal doesn't thaw on set, seems like both should (don't know if reactiveValues does)
  3. Should we auto-unset all input$setMeta for a given slot when that slot is written to?
@jcheng5
Copy link
Member Author

jcheng5 commented Jul 17, 2020

Here's an example of freezeReactiveValue not behaving correctly with a textInput that is re-rendered with its own value:

library(shiny)

ui <- fluidPage(
  uiOutput("ui"),
  actionButton("redraw", "Redraw"),
  p("Status:", textOutput("status", inline = TRUE))
)

server <- function(input, output, session) {
  output$ui <- renderUI({
    input$redraw
    freezeReactiveValue(input, "outval")
    textInput("outval", "Dynamic input", value = "hello")
  })
  
  output$status <- renderText({
    input$redraw
    tryCatch({
      input$outval
      "Thawed"
    }, error = function(err) {
      "Frozen"
    })
  })
}

shinyApp(ui, server)

If you click "Redraw" without changing the value from "hello", then the output only sees the input as frozen. The correct behavior would be for the input to only be frozen for a brief moment (the time between output$ui being refreshed and the text input being re-bound). The reason for this is because when the text input is re-bound, its value is the same as the last known value for the "outval" input, so nothing is sent to the server.

One solution for this would be for every bindInput to send values to the server regardless of whether it's a duplicate of the last value or not.

@jcheng5
Copy link
Member Author

jcheng5 commented Jul 17, 2020

Similar problem as my previous comment, but this time with updateXXXInput:

library(shiny)

ui <- fluidPage(
  textInput("outval", "Dynamic input", value = "hello"),
  actionButton("update", "Update"),
  p("Status:", textOutput("status", inline = TRUE))
)

server <- function(input, output, session) {
  observeEvent(input$update, {
    freezeReactiveValue(input, "outval")
    updateTextInput(session, "outval", value = "hello")
  })

  output$status <- renderText({
    input$update
    tryCatch({
      input$outval
      "Thawed"
    }, error = function(err) {
      "Frozen"
    })
  })
}

shinyApp(ui, server)

The previous solution I proposed would not help for this case.

jcheng5 added a commit that referenced this issue Sep 15, 2020
1. freezeReactiveValue(input, "x") is called, inside a renderUI
   or in an observer that then calls updateXXXInput
2. Some reactive output tries to access input$x, this takes a
   reactive dependency but throws a (silent) error
3. When the flush cycle ends, it automatically thaws

What's *supposed* to happen next is the client receives the new
UI or updateXXXInput message, which causes input$x to change,
which causes the reactive output to invalidate and re-run, this
time without input$x being frozen.

This works, except when the renderUI or updateXXXInput just so
happens to set input$x to the same value it already is. In this
case, the client would detect the duplicate value and not send
it to the server. Therefore, the reactive output would not be
invalidated, and effectively be "stalled" until the next time it
is invalidated for some other reason.

With this change, freezeReactiveValue(input, "x") has a new side
effect, which is telling the client that the very next update to
input$x should not undergo duplicate checking.
jcheng5 added a commit that referenced this issue Sep 18, 2020
1. freezeReactiveValue(input, "x") is called, inside a renderUI
   or in an observer that then calls updateXXXInput
2. Some reactive output tries to access input$x, this takes a
   reactive dependency but throws a (silent) error
3. When the flush cycle ends, it automatically thaws

What's *supposed* to happen next is the client receives the new
UI or updateXXXInput message, which causes input$x to change,
which causes the reactive output to invalidate and re-run, this
time without input$x being frozen.

This works, except when the renderUI or updateXXXInput just so
happens to set input$x to the same value it already is. In this
case, the client would detect the duplicate value and not send
it to the server. Therefore, the reactive output would not be
invalidated, and effectively be "stalled" until the next time it
is invalidated for some other reason.

With this change, freezeReactiveValue(input, "x") has a new side
effect, which is telling the client that the very next update to
input$x should not undergo duplicate checking.
jcheng5 added a commit that referenced this issue Oct 6, 2020
1. freezeReactiveValue(input, "x") is called, inside a renderUI
   or in an observer that then calls updateXXXInput
2. Some reactive output tries to access input$x, this takes a
   reactive dependency but throws a (silent) error
3. When the flush cycle ends, it automatically thaws

What's *supposed* to happen next is the client receives the new
UI or updateXXXInput message, which causes input$x to change,
which causes the reactive output to invalidate and re-run, this
time without input$x being frozen.

This works, except when the renderUI or updateXXXInput just so
happens to set input$x to the same value it already is. In this
case, the client would detect the duplicate value and not send
it to the server. Therefore, the reactive output would not be
invalidated, and effectively be "stalled" until the next time it
is invalidated for some other reason.

With this change, freezeReactiveValue(input, "x") has a new side
effect, which is telling the client that the very next update to
input$x should not undergo duplicate checking.
@fweber144
Copy link

Isn't this fixed and could be closed?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants