I am working on a shiny app that periodically checks a Github repo where I store the data for new pushes (i.e. new data arrived), but only reruns the calculations if new data arrived.
My problem is that if I use invalidateLater in a reactive to check for the push time, and I use that reactive to trigger a reactiveEvent that runs the calculations, the reactiveEvent is triggered even, if the push time itself did not change.
I made a small reprex with a constant push time.
Do you have any suggestions on how to solve this problem?
Thanks!
shinyApp(
ui = fluidPage(
plotOutput("plot")
),
server = function(input, output, session) {
# Get latest update time
push_time <- reactive({
invalidateLater(1000)
# In the real code here I get the latest push
# time from a Github repo
# For reprex here is a unix timestamp
1601627006
})
# Update data only if push_time is updated
# i.e. new data arrived
my_data <- eventReactive(push_time(), {
runif(1000, 0, 1)
})
# Render plot
output$plot <- renderPlot(plot(my_data()))
}
)
I think what you are looking for is a reactive value. The calling reactive expr will depend on the value. What you've done here is a reactive expression that gets invalidated although it is replaced by the same expression.
library(shiny)
shinyApp(
ui = fluidPage(
plotOutput("plot")
),
server = function(input, output, session) {
# init with any value, here your value
push_time <- reactiveVal(1601627006)
# I don't like unspecific observers but I could not think of any better for the moment
observe({
invalidateLater(1000)
# print every tick
print(sprintf("%s: Tick. Value: %s", Sys.time(), isolate(push_time())))
# mimic an update by chance
if (runif(1) > 0.8) {
# update the value
push_time(1601627006)
} else {
push_time(0)
}
})
# Update data only if push_time is updated
# i.e. new data arrived
my_data <- eventReactive(push_time(), {
print(sprintf("%s: Update. Value: %s", Sys.time(), isolate(push_time())))
runif(1000, 0, 1)
})
# Render plot
output$plot <- renderPlot(plot(my_data()))
}
)