Reputation: 45
I am trying to read a file after taking inputs from user - first a date and then a selection of file, but I can't get the code read any file and do anything with it. The Error message is following. Also is there a way to make this code more efficient?
ui <- fluidPage(
titlePanel("Select the execution date")
,dateInput("ME_DATE",label=h3("Execution Date Input"), value="2020-05-29")
,hr()
,fluidRow(column(3,verbatimTextOutput("Output_path")))
,hr()
,selectInput('selectfile','Select File in Above Location', choices=NULL)
,textOutput('fileselection_statement')
,tableOutput('selected_table')
)
server <- function(input, output, session) {
# Location for Outputs
Output_DIR <- "K:/Outputs/"
Output_loc <- reactive({
year_N_ME_DATE <- format(input$ME_DATE,"%Y")
month_N_ME_DATE <- format(input$ME_DATE,"%m")
month_T_ME_DATE <- months(input$ME_DATE)
file.path(paste(Output_DIR,month_N_ME_DATE,". ",month_T_ME_DATE, " ",year_N_ME_DATE,"/",sep=""))
})
# Output Path
output$Output_path <- renderPrint({ Output_loc() })
# files list
Updated_Output_files_list <- reactive({ list.files(Output_loc()) })
observeEvent(input$selectfile, {
updateSelectInput(session, "selectfile", choices=Updated_Output_files_list())
output$fileselection_statement <- renderText({paste0('You have selected: ', input$selectfile) })
})
selectfile <- reactive(get(input$selectfile))
output$selected_table <- renderTable({ read.csv(paste0(renderPrint({ Output_loc() }),renderPrint({ selectfile() }),sep="")) })
}
shinyApp(ui, server)
Upvotes: 0
Views: 818
Reputation: 161065
(Since changed) Make the block containing file.path(.)
a reactive
block and assign it to something so that other reactive components can use it. In your case, you changed it to Output_loc
, so other blocks will refer to it as Output_loc()
.
Similarly, you cannot put output$... <-
assignments or render*
calls inside an observe
or observeEvent
block. So we'll move your output$fileselection_statement
outside of the observeEvent
.
renderPrint
is its own rendering function, on the same level as renderTable
. You cannot nest them. In this case, I'm just going to remove them from inside the renderTable
call, they make no sense there.
This case did not need selectfile <- reactive(get(input$selectfile))
, there is no apparent gain in that indirection. Just use input$selectfile
. Removed.
After fixing all of the above, it is also the case that you were updating the selectInput
every time the selectInput
was changed, which is incorrect (and completely disallows any real use of this). Instead, you want to update it when the Updated_Output_files_list()
changes.
Also, instead of repeatedly concatenating the path together to create the file to be read, I use list.files(..., full.names=TRUE)
. This will be a named vector, where the values are the full path and filename, but the names will be just the filename (no leading path). This useful because selectInput
displays the name but returns the value (full path). There is rarely a time when I think not specifying full.names=TRUE
is the right thing (I cannot think of any right now).
Here's a working copy. It is not perfectly-awesome, there are still areas where some grooming might be in order.
server <- function(input, output, session) {
# Location for Outputs
Output_DIR <- "K:/Outputs/"
Output_loc <- reactive({
year_N_ME_DATE <- format(input$ME_DATE, "%Y")
month_N_ME_DATE <- format(input$ME_DATE, "%m")
month_T_ME_DATE <- months(input$ME_DATE)
file.path(Output_DIR,
paste0(month_N_ME_DATE, ". ", month_T_ME_DATE, " ", year_N_ME_DATE),
"/")
})
# alternative
# Output_loc <- reactive({
# file.path(Output_DIR, format(Sys.Date(), format = "%m. %b %Y"))
# })
# Output Path
output$Output_path <- renderPrint({ req(Output_loc()) })
# files list
Updated_Output_files_list <- reactive({
lf <- list.files(Output_loc(), full.names = TRUE)
names(lf) <- basename(lf)
# in this example, 'lf' is now:
# c(iris.csv = "K:/Outputs/05. May 2020/iris.csv", mtcars.csv = "K:/Outputs/05. May 2020/mtcars.csv")
# ... the *name* will be displayed in the selectInput, but the
# *full path* will be the value of the selection
lf
})
output$fileselection_statement <- renderText({
paste0('You have selected: ', input$selectfile)
})
observeEvent(Updated_Output_files_list(), {
updateSelectInput(session, "selectfile", choices = Updated_Output_files_list())
})
output$selected_table <- renderTable({
req(input$selectfile)
read.csv(input$selectfile)
})
}
Upvotes: 1