45

I have a complex Shiny app spread across multiple files that uses code from several packages. The app works when run locally in R Studio, but on my server it throws a generic error:

Error: do not know how to convert 'x' to class "Date"

This is probably a simple programming mistake, but figuring out exactly where that mistake is in the code is proving difficult.

How can I hunt down and fix the source of errors in Shiny apps? And what tools are available to do this in a systematic way?


There has been some discussion of similar problems on Google Groups.

sdgfsdh
  • 33,689
  • 26
  • 132
  • 245

4 Answers4

56

You can achieve logging on the server using a combination of logging and shinyjs.

install.packages("logging")
install.packages("shinyjs")

In your ui.R, bind shinyjs using shinyjs::useShinyjs:

library(shinyjs)

shinyUI(
    fluidPage(
        useShinyjs(),
# etc...

In your server.R, add logjs to the list of log handlers:

library(magrittr)
library(shinyjs)
library(logging)

basicConfig()

options(shiny.error = function() { 
    logging::logerror(sys.calls() %>% as.character %>% paste(collapse = ", ")) })

shinyServer(function(input, output, session) {

    printLogJs <- function(x, ...) {

        logjs(x)

        T
    }

    addHandler(printLogJs)
# etc...

Then to print something, use loginfo.

Other Tips

  1. When running your app locally, such as from RStudio, use options(shiny.error = browser) or options(shiny.error = recover) to identify the source of errors.

  2. Put as much business logic into packages and external scripts as possible. Unit-test these whenever you suspect they are causing issues. The testthat package can help here.

  3. If you expect a variable to meet certain constraints, add an assertion. For example, if x should be a zoo, put assert_that(is.zoo(x)) near the top of your reactive.

  4. Beware of the default drop behaviour. Get into the habit of specifying drop = F whenever you want your result to be a data.frame.

  5. Try to minimize the number of variables (options, environment, caching, UI state, etc.) that a unit of code depends on. Weakly typed languages are hard enough to debug already!

  6. Use proper S4 and S3 classes instead of raw R structures where possible.

  7. dput will allow you to examine the internal structure of objects, and is very useful when trying to reproduce errors outside of an app.

  8. Try to do your debugging in an interactive console, not using print inside an app. This will allow you to iterate more quickly. When debugging outside of an app is not possible, try putting a browser() call just before the problem code.

  9. Never use sapply in non-interactive code. With an empty output, it will be unable to infer the type that you want and return an empty list. If your result should be a vector, use vapply. If your result should be a list, use lapply.

You should also look at Debugging Shiny Applications from the RStudio team.

sdgfsdh
  • 33,689
  • 26
  • 132
  • 245
15

I'm surprised that the RStudio Shiny debug article is not mentioned. That article is very thorough in debugging and error processing.

You can check the log of your server, which should solve the question asked by OP more directly.

dracodoc
  • 2,603
  • 1
  • 23
  • 33
6

Date issue: The server side could be using a different operating system, with a different default character set encoding (e.g. "latin1", "utf-8"). Sometimes, loading data in R loses encoding. The function read.csv has a parameter encoding="UTF-8", which you could use.

To debug, I have relied on print statements. I'm also interested to know if others have found a more systematic way.

maurice
  • 836
  • 7
  • 5
  • Yes, the server is running Linux but my machine is Windows. How do you get the `print` statements to display in the browser console? – sdgfsdh Aug 10 '15 at 13:55
  • 2
    The print statements would show in the R console. While rudimentary, simple "got to this part" and " got to that part " statements helped me debug. I was using RStudio, and running runApp() to display the app in a Chrome browser. – maurice Aug 11 '15 at 14:21
  • Yes that is an option in RStudio, but it is not possible when running on a remote server. – sdgfsdh Aug 11 '15 at 15:11
  • I believe the print statements show in the server logs. You may need help from the server administrator to access these logs. – Josiah Yoder Jul 21 '20 at 18:26
0
options(shiny.error = browser)

Add above line and run the code, when there is error it would stop and you can search in stacktace as shown below

enter image description here

vishal
  • 855
  • 1
  • 8
  • 16