Shiny + downloadHandler + Openxlsx не создает файл xlsx
Я пытаюсь сгенерировать файл.xlsx через пакет Openxlsx с реактивным именем и заголовком внутри файла (входными переменными являются "ASL.1" и "Year.1"). Объектом, который будет сохранен в файле, является реактивная таблица "tab_1 ()", которая генерируется приложением без каких-либо проблем, но когда я пытаюсь загрузить ее, имя, которое генерируется браузером (Chrome), не является (т.е.) "Tab_1_TOSCANA_2015".xlsx"но"download_tab_1", outputId кнопки" скачать "связан, и ничего не генерируется. Я не понимаю, где проблема, так как я проверил другие подобные примеры с Openxlsx и не вижу ошибок в моем сценарии, если я пытаюсь записать файл.csv с помощью команды "write.csv", все работает.
Сценарий находится здесь: https://drive.google.com/drive/folders/1dSI9qWgQyShjXjkJ2B6COuWzuWZie5IP?usp=sharing
Приложение (это только небольшая часть)
https://cerimp-open-data.shinyapps.io/Malprof/
require(shiny)
require(dplyr)
require(reshape2)
require(stringr)
require(shinythemes)
require(ggplot2)
require(openxlsx)
require(leaflet)
require(RColorBrewer)
require(rgdal)
require(rgeos)
require(maptools)
load("dati.RData")
#### UI ####
ui <- fluidPage(
theme = shinytheme("spacelab"),
titlePanel("Indice"),
navlistPanel(
#### Tab I ####
tabPanel(title = "Tab. I Tassi per ASL di competenza e Sesso",
h1(textOutput(outputId = "tab_1_text"), style = "font-size:100%"),
fluidRow(column(3, selectInput(inputId = "ASL.1",
label = "Territorio",
choices = list("TOSCANA", "ASL CENTRO","ASL NORD-OVEST","ASL SUD-EST"),
selected = "Toscana",
multiple = FALSE)),
column(3, selectInput(inputId = "Anno.1",
label = "Anno di manifestazione",
choices = as.list(unique(malprof$Anno)),
selected = max(malprof$Anno),
multiple = FALSE))),
fluidRow(column(2, downloadButton(outputId = "download_tab_1",
label = "Scarica i dati"))),
div(tableOutput(outputId = "tab_1"), style = "font-size:80%")
),
#### Fig 1 ####
tabPanel(title = "Fig. 1 Andamento delle denunce INAIL e delle segnalazioni Malprof",
h1(textOutput(outputId = "fig_1_text"), style = "font-size:100%"),
fluidRow(column(3, selectInput(inputId = "ASL.fig.1",
label = "Territorio",
choices = list("TOSCANA", "ASL CENTRO","ASL NORD-OVEST","ASL SUD-EST"),
selected = "Toscana",
multiple = FALSE))),
div(plotOutput(outputId = "fig.1"), style = "font-size:80%")
)
)
#### SERVER ####
server <- function(input, output) {
fargs <- list(big.mark=".", decimal.mark=",") #parametri per la formattazione dei numeri nelle tabelle
annoUltimo <- max(malprof$Anno)
rg <- filter(malprof, ASL == "TOSCANA")
no <- filter(malprof, ASL == "ASL NORD-OVEST")
se <- filter(malprof, ASL == "ASL SUD-EST")
ce <- filter(malprof, ASL == "ASL CENTRO")
#### Tabella I - Distribuzione di frequenza delle segnalazioni di MP e dei relativi tassi per 100.000 abitanti suddivisi per ASL di competenza e Sesso ####
selezioneASL.1 <- reactive({switch(input$ASL.1,
"TOSCANA" = rg,
"ASL CENTRO" = ce,
"ASL NORD-OVEST" = no,
"ASL SUD-EST" = se)})
tab.1 <- reactive({
pop <- popTosc %>% filter(Anno == input$Anno.1) %>%
dcast(EXASL ~ SEX, drop = T, fill = 0, fun.aggregate = sum, value.var = "N") %>%
filter(!is.na(EXASL))
mp <- selezioneASL.1() %>% filter(Anno == input$Anno.1) %>%
dcast(EXASL ~ sesso_lav, drop = T, fill = 0, fun.aggregate = length, value.var = "Anno")
tab <- pop %>% inner_join(mp, by = c("EXASL" = "EXASL")) %>%
mutate(T_F = round((F.y/F.x)*100000, 1),
T_M = round((M.y/M.x)*100000, 1)) %>%
select(EXASL, F.x, M.x, F.y, M.y, T_F, T_M)
tab.tot <- c("TOTALE", sum(tab$F.x), sum(tab$M.x), sum(tab$F.y), sum(tab$M.y), round((sum(tab$F.y)/sum(tab$F.x))*100000, 1), round((sum(tab$M.y)/sum(tab$M.x))*100000, 1))
tab <- rbind(tab, tab.tot)
tab$F.x <- as.numeric(tab$F.x)
tab$M.x <- as.numeric(tab$M.x)
tab$F.y <- as.numeric(tab$F.y)
tab$M.y <- as.numeric(tab$M.y)
tab$T_F <- as.character(tab$T_F)
tab$T_M <- as.character(tab$T_M)
tab <- rename(tab, "EXASL" = EXASL, "Pop. F" = F.x, "Pop. M" = M.x, "Segn. F" = F.y, "Segn. M" = M.y, "Tasso - F" = T_F, "Tasso - M" = T_M)
tab
})
output$tab_1_text <- renderText(paste0("Distribuzione di frequenza delle segnalazioni di MP e dei relativi tassi per 100.000 abitanti suddivisi per ASL di competenza e Sesso - ", input$ASL.1, ", ", input$Anno.1, "."))
output$tab_1 <- renderTable({tab.1()},
display=c("s","s","d","d","d","d","s","s"),
spacing="s",
align = 'lcccccc',
na="--", format.args=fargs)
output$download_tab_1 <- downloadHandler(
filename = function() {
paste("Tab_1_", input$ASL.1, "_", input$Anno.1, ".xlsx", sep = "")
},
content = function(file) {
wb <- createWorkbook()
addWorksheet(wb, sheetName = "Dati", gridLines = TRUE)
intestazione <- paste0("Distribuzione di frequenza delle segnalazioni di MP e dei relativi tassi per 100.000 abitanti suddivisi per ASL di competenza e Sesso - ", input$ASL.1, ", ", input$Anno.1, ".")
writeData(wb, 1, x = intestazione)
writeDataTable(wb, sheet = 1, startRow = 3, x = tab.1(), colNames = TRUE)
saveWorkbook(wb, file)
}
)
}
# Run the application
shinyApp(ui = ui, server = server)
1 ответ
Я работал над тем, что звучит как та же проблема. Это было вызвано проблемой, с которой скачивал пакет openxlsx downloadHandler (Shiny). Не работало ни количество исправлений, ни обеспечение того, чтобы пакет находился в правильной папке. Насколько мы могли понять, это проблема с обработчиком загрузки Shiny, взаимодействующим с openxlsx.
В конце я исправил это, сохранив локальную временную версию XLSX, а затем сослался на это в downloadHandler.
Переместите этот раздел (внутри downloadHandler) за пределы обработчика загрузки:
addWorksheet(wb, sheetName = "Dati", gridLines = TRUE)
intestazione <- paste0("Distribuzione di frequenza delle segnalazioni di MP e dei relativi tassi per 100.000 abitanti suddivisi per ASL di competenza e Sesso - ", input$ASL.1, ", ", input$Anno.1, ".")
writeData(wb, 1, x = intestazione)
writeDataTable(wb, sheet = 1, startRow = 3, x = tab.1(), colNames = TRUE)
saveWorkbook(wb, file)
Затем внутри обработчика используйте версию этого:
output$downloadData <- downloadHandler(
filename = function(){paste0(intestazione,".xlsx")},
content = function(file) {
file.copy(filename,file)
#file.rename(fname,file)
}
)
Я думаю, что я могу заставить его работать, просто ссылаясь на файл в функции saveWorkbook внутри обработчика загрузки...
Это работает с пакетом openxlsx и Shiny downloadHandler:
output$quick_export <- downloadHandler(
filename = "my export.xlsx",
content = function(file) {
wb <- createWorkbook()
addWorksheet(wb, "Cars")
x <- mtcars[1:6, ]
writeData(wb, "Cars", x, startCol = 2, startRow = 3, rowNames = TRUE)
saveWorkbook(wb, file, overwrite = TRUE)
}
)