I am not good at English, so sentences may be wrong.
I want to distribute excel files prepared in advance to users. Is it possible to realize such a system with shiny? No problem with .zip.
Thank you
ui.R
shinyUI(
fluidPage(
downloadButton('downloadData', 'Excel Download')
)
)
server.R
shinyServer(function(input, output) {
output$downloadData <- downloadHandler(
filename = "distribution.xlsx",
content = "distribution_excel"
)
})
Yes, it is possible and you were nearly there. Below is a minimal working example. I assume that your .xlsx file is located in the same folder as your app.R. Notice that I have created the app in a single R file as opposed to two separate files.
The trick to getting the file to download is to use a function for the content inside of downloadHandler(). Specifically we are using the base function file.copy(). Clicking the button should now download the file: distribution.xlsx. This file can obviously be exchanged with a zip file.
If you want different users to access different Excel files, you can write an additional function inside of your server function that passes the file argument to the downloadHandler().
# Load packages ----
pkgs <- c("shiny")
invisible(lapply(pkgs, require, character.only = TRUE))
# Set up the UI ----
ui <- fluidPage(
# Define your download button
downloadButton(
outputId = "downloadData",
label = "Excel Download"
)
)
# Set up the server side ----
server <- function(input, output, session) {
# Define the download handler with function() for content.
output$downloadData <- downloadHandler(
filename = "distribution.xlsx",
content = function(file) {
file.copy("distribution.xlsx", file)
}
)
}
# Combine into an app ----
shinyApp(ui = ui, server = server)
Related
I'm building a Shiny App where users complete a survey, and based on their responses, it suggests different templates for them to use. The templates are all excel files that are heavily formatted (e.g., have pictures on them, misaligned headings, etc.), like the screenshot that I've uploaded here. Unfortunately, stackoverflow won't let me upload the excel file to make this fully reproducible, but if you can run it with any non-tabular excel file, it'll work.[![enter image description here][1]][1]
These templates are all uploaded to the server, and the users input does not affect them. I've tried following the example by others, like this [one][2], but I keep getting errors.
How do I get it so when users click the download button, they get the excel file exactly as it appears?
library(readxl)
library(shiny)
library(writexl)
ui <- fluidPage(
sidebarLayout(
sidebarPanel(
),
mainPanel(
downloadButton("downloadData", "Download Fancy Excel File")
)))
server <- function(input, output) {
output$downloadData <- downloadHandler(
filename = function() {
paste("file", "xlsx", sep='')
},
content = function(file) {
myfile <- srcpath <- 'Home/Other Layer/Fancy Template.xlsx'
file.copy(myfile, file)
}
)
}
# Run the application
shinyApp(ui = ui, server = server)
~~~~
[1]: https://i.stack.imgur.com/FK034.png
[2]: https://stackoverflow.com/questions/39449544/shiny-download-an-excel-file
You are missing a . in the file name. Also, you can keep all the files you want the users to download in www folder. The following works for me.
ui <- fluidPage(
sidebarLayout(
sidebarPanel(
),
mainPanel(
downloadButton("downloadData", "Download Fancy Excel File")
)))
server <- function(input, output) {
output$downloadData <- downloadHandler(
filename = function() {
paste("testfile", ".xlsx", sep='')
},
content = function(file) {
# myfile <- srcpath <- 'Home/Other Layer/Fancy Template.xlsx'
myfile <- srcpath <- "./www/test141.xlsx"
file.copy(myfile, file)
}
)
}
# Run the application
shinyApp(ui = ui, server = server)
I am learing Shiny. I want to make a simple app that allows for dynamic paths that the user enters. The app should then list csv files in folder A and then copy them from folder A to folder B (the working directory). Then the app does some operations in folder B using an external exe program. Afterwards the folder will cut the results files (.txt) from B and copies them into A.
The structure of my app is as follows ( I have also attached a picture). the problem is explained in the comments in the code.
library(shiny)
ui<-fluidPage(
textInput("prg","Program",getwd()),
verbatimTextOutput("prg"),
textInput("prj","Project","Project"),
verbatimTextOutput("prj")
)
server<-function(input, output,session) {
output$prg=renderText(input$prg)
renderPrint(output$prg)
output$prj=renderText(paste0(input$prg,"/",input$prj))
#This is where my challenge is
#I want to
#list.files(path=path-shown-in-text-box-Project,pattern=".csv")
#Then i want to copy csv files from A to B as described above and run the following program
#This works
observeEvent(input$run,
{
system("my.exe") #exe not shared
})
#Finally I want to cut and paste the results (.txt) from B back into A
}
shinyApp(ui,server)
I want to list.files(path=path-shown-in-text-box-Project,pattern=".csv")
Here's code you can use to browse any directory for a particular CSV file, read that file and display its contents.
library(shiny)
# Define UI
ui <- pageWithSidebar(
# App title ----
headerPanel("Open a File and Show Contents"),
# Sidebar panel for inputs ----
sidebarPanel(
label="Data Source",fileInput("fileName", "File Name",accept=c(".csv"))),
# Main panel for displaying outputs ----
mainPanel(
tableOutput(outputId = "table")
)
)
# Define server logic
server <- function(input, output) {
inputData <- reactive ({
if (is.null(input$fileName)) return(NULL)
inFile <- input$fileName
conInFile <- file(inFile$datapath,open='read')
inData <- read.csv(conInFile,stringsAsFactors = FALSE)
close (conInFile)
return (inData)
})
output$table <- renderTable ({
inData <- inputData()
if (length(inData) > 0) inData
})
}
shinyApp(ui, server)
I am almost done creating a survey using Rshiny. I want to create a button that will allow the user to upload an image (jpeg,tiff,png etc) to the R shiny server, Dropbox, or google drive. It seems the fileInput method only accepts documents like csv? any help would be appreciated!
fileInput actually allows the import of any type of files. You just need to set the argument accept to NULL or to any file extension that you accept. What you need to understand first, is that if you use fileInput, it will actually upload your file to the tmp folder (the path to the uploaded data is stored in input$file$datapath), and only then you will be able to upload your file to googledrive or to whatever cloud. A solution using fileInput could look like this:
library(googledrive)
ui <- fluidPage(
fileInput(inputId = "file",
label = "Choose file to upload",
accept = NULL)
)
server <- function(input, output) {
observeEvent(input$file, {
drive_upload(media = input$file$datapath,
name = input$file$name)
})
}
shinyApp(ui, server)
If the "double upload" is a problem for you, you can avoid this by using the package shinyFiles. A nice answer has been posted here and here's a way to adapt the code to address your specific problem.
library(googledrive)
library(shinyFiles)
ui <- fluidPage(
shinyFilesButton("Btn_GetFile", "Choose file to upload" ,
title = "Please select a file:", multiple = FALSE,
buttonType = "default", class = NULL)
)
server <- function(input, output, session) {
volumes = getVolumes()
observe({
shinyFileChoose(input, "Btn_GetFile", roots = volumes, session = session)
if (!is.null(input$Btn_GetFile)){
file_selected <- parseFilePaths(volumes, input$Btn_GetFile)
drive_upload(media = as.character(file_selected$datapath),
name = as.character(file_selected$name))
}
})
}
shinyApp(ui = ui, server = server)
The download handler is a remarkably popular shiny tool - even for local work. However it is quite annoying when it opens up all the time in the R-Studio directory. Here is the current example program from the Shiny documantion.
library(shiny)
## Only run examples in interactive R sessions
if (interactive()) {
ui <- fluidPage(
downloadLink("downloadData", "Download")
)
server <- function(input, output) {
# Our dataset
data <- mtcars
output$downloadData <- downloadHandler(
filename = function() {
paste("data-", Sys.Date(), ".csv", sep="")
},
content = function(file) {
write.csv(data, file)
}
)
}
shinyApp(ui, server)
}
It opens like this:
A few related questions:
Is there anyway to override that directory to something more reasonable?
Can I specify the default name anywhere (the default is a bit bizarrely take from the name of the output list name).
Any insights as to why this is so would be welcome. There seems to be nothing in the docs around this.
I am new to shiny and was wondering if there is a way to display a pdf file generated in "downloadHandler"?
I am using a package to do some biological analysis, and I can make it create a pdf file in downloadHandler. However, I am still struggling if I can view this pdf instead of downloading it.
This question is related to Shiny to output a function that generates a pdf file itself.
Please see the below for the code that works for downloading the pdf output. Thanks so much!
library(shiny)
library(msa)
runApp(list(
#Load the exmaple from the msa package.
mySequenceFile <- system.file("examples", "exampleAA.fasta", package="msa"),
mySequences <- readAAStringSet(mySequenceFile),
myFirstAlignment <- msa(mySequences),
# A simple shiny app.
# Is it possible to see the generated pdf file on screen?
ui = fluidPage(downloadButton('downloadPDF')),
server = function(input, output) {
output$downloadPDF = downloadHandler(
filename = 'myreport.pdf',
content = function(file) {
msaPrettyPrint(
myFirstAlignment
, file = 'myreport.pdf'
, output="pdf"
, showNames="left"
, showLogo="top"
, consensusColor="BlueRed"
, logoColors="accessible area"
, askForOverwrite=FALSE)
file.rename("myreport.pdf", file) # move pdf to file for downloading
},
contentType = 'application/pdf'
)
}
))
If you intend to display the pdf, you should not use downloadHandler. Instead, just use your pdf printing function to generate the pdf file, but the key is
Create a www folder under your Shiny project root
Point the file argument of msaPrettyPrint to www/myreport.pdf
Dynamically add an iframe to display the file. Note in the iframe you point to myreport.pdf directly without www, as Shiny automatically looks for static/media files inside the www folder.
See below for a working example (note I am not using the msa package here but the idea should be the same).
library(shiny)
ui <- shinyUI(fluidPage(
titlePanel("Old Faithful Geyser Data"),
sidebarLayout(
sidebarPanel(
actionButton("generate", "Generate PDF")
),
mainPanel(
uiOutput("pdfview")
)
)
))
server <- shinyServer(function(input, output) {
observeEvent(input$generate, {
output$pdfview <- renderUI({
pdf("www/myreport.pdf")
hist(rnorm(100))
dev.off()
tags$iframe(style="height:600px; width:100%", src="myreport.pdf")
})
})
})
shinyApp(ui = ui, server = server)