Question

I set up a shiny app that checks for a GET string and presents a link if a file matching the id argument exists. Now what I would like to do is have the page redirect straight to the download file if a valid query is detected in the URL. Does anybody know of the syntax to insert, e.g. a <meta http-equiv=...> header from server.R?

Motivation: I want to be able to download files directly into an R console session from a URL pointing at a Shiny app. So, a non-geeky user specifies their preliminary statistical model using Shiny, then a statistician downloads it into their usual working environment and takes it the rest of the way. I need to do this server-side rather than with something like javascript's window.location because javascript won't be supported client-side.

Here is the server.R

shinyServer(function(input, output, clientData) {
  query <- reactive(parseQueryString(clientData$url_search));
  revals <- reactiveValues();

  ## obtain ID from GET string 
  observe({revals$id <- query()$id}); 

  ## alternatively obtain ID from user input if any
  observe({input$submitid; if(length(id<-isolate(input$manualid))>0) revals$id <- id;}); 

  ## update filename, path, and existance flag
  observe({ revals$filename <- filename <- paste0(id<-revals$id,".rdata");
    revals$filepath <- filepath <- paste0("backups/",filename);
    revals$filexists <- file.exists(filepath)&&length(id)>0; });

  ## update download handler
  output$download <- {downloadHandler(filename=function() revals$filename, content=function(oo) if(revals$filexists) system(sprintf('cp %s %s',revals$filepath,oo)))};

  ## render the download link (or message, or lack thereof)
  output$link <- renderUI({
    cat('writing link widget\n');
    id<-revals$id;
    if(length(id)==0) return(div(""));
    if(revals$filexists) list(span('Session download link:'),downloadLink('download',id)) else {
      span(paste0("File for id ",id," not found"));}});
});

Here is the ui.R

shinyUI(pageWithSidebar(
          headerPanel(div("Banner Text"),"Page Name"),
          sidebarPanel(),
          mainPanel(
            htmlOutput('link'),br(),br(),
            span(textInput('manualid','Please type in the ID of the session you wish to retrieve:'),actionButton('submitid','Retrieve')))));

Update:

In trying @jeff-allen 's suggestion, I ran into another problem: how to extract the filesystem path to which the files get copied for downloading and turn it into a valid URL? It's probably possible by screwing with shell scripts and http config settings on my local host, but how to do this in a portable way that doesn't require superuser privileges and is as shiny-native as possible?

Was it helpful?

Solution

Motivation: I want to be able to download files directly into an R console session from a URL pointing at a Shiny app.

...i.e. this amounts to a very roundabout way of trying to serve static content from a shiny app. Turns out I don't need to redirect or use downloadHandler at all. As this post on the Shiny forum says, any file I create inside the local www directory will be accessible as if it is at the root of my app directory. I.e. if I have my app do save.image(file='www/foo.rdata') then I will be able to access it from [http://www.myhost.com/appname/foo.rdata] if the app itself lives at [http://www.myhost.com/appname/]

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top