web-dev-qa-db-fra.com

Débogage efficace des applications Shiny

J'ai une application Shiny complexe répartie sur plusieurs fichiers qui utilise le code de plusieurs packages. L'application fonctionne lorsqu'elle est exécutée localement dans R Studio, mais sur mon serveur, elle génère une erreur générique:

Erreur: je ne sais pas comment convertir 'x' en classe "Date"

Il s'agit probablement d'une simple erreur de programmation, mais il est difficile de déterminer exactement cette erreur se trouve dans le code.

Comment puis-je traquer et corriger la source des erreurs dans les applications Shiny? Et quels outils sont disponibles pour le faire de manière systématique?


Il y a eu des discussions sur des problèmes similaires sur Google Groupes .

32
sdgfsdh

Vous pouvez réaliser la journalisation sur le serveur en utilisant une combinaison de logging et shinyjs.

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

Dans votre ui.R, liez shinyjs en utilisant shinyjs::useShinyjs:

library(shinyjs)

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

Dans votre server.R, ajoutez logjs à la liste des gestionnaires de journaux:

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...

Ensuite, pour imprimer quelque chose, utilisez loginfo.

Autres conseils

  1. Lorsque vous exécutez votre application localement, par exemple depuis RStudio, utilisez options(shiny.error = browser) ou options(shiny.error = recover) pour identifier la source des erreurs.

  2. Mettez autant de logique métier que possible dans les packages et les scripts externes. Testez-les à chaque fois que vous soupçonnez qu'ils causent des problèmes. Le package testthat peut vous aider ici.

  3. Si vous vous attendez à ce qu'une variable réponde à certaines contraintes, ajoutez une assertion. Par exemple, si x doit être un Zoo, placez assert_that(is.Zoo(x)) vers le haut de votre réactif.

  4. Méfiez-vous du comportement par défaut drop. Prenez l'habitude de spécifier drop = F Chaque fois que vous voulez que votre résultat soit un data.frame.

  5. Essayez de minimiser le nombre de variables (options, environnement, mise en cache, état de l'interface utilisateur, etc.) dont dépend une unité de code. Les langues mal typées sont déjà assez difficiles à déboguer!

  6. Utilisez les classes S4 et S3 appropriées au lieu des structures R brutes dans la mesure du possible.

  7. dput vous permettra d'examiner la structure interne des objets et est très utile lorsque vous essayez de reproduire des erreurs en dehors d'une application.

  8. Essayez de faire votre débogage dans une console interactive, sans utiliser print dans une application. Cela vous permettra d'itérer plus rapidement. Lorsque le débogage en dehors d'une application n'est pas possible, essayez de placer un appel browser() juste avant le code du problème.

  9. Jamais utilisez sapply dans du code non interactif. Avec une sortie vide, il ne pourra pas déduire le type souhaité et retourner un list vide. Si votre résultat doit être un vector, utilisez vapply. Si votre résultat doit être un list, utilisez lapply.

Vous devriez également regarder Debugging Shiny Applications de l'équipe RStudio.

47
sdgfsdh

Je suis surpris que l'article de débogage de RStudio Shiny ne soit pas mentionné. Cet article est très complet dans le débogage et le traitement des erreurs.

Vous pouvez consulter le journal de votre serveur, ce qui devrait résoudre la question posée par OP plus directement.

10
dracodoc

Problème de date: le côté serveur peut utiliser un système d'exploitation différent, avec un codage de jeu de caractères par défaut différent (par exemple, "latin1", "utf-8"). Parfois, le chargement de données dans R perd l'encodage. La fonction read.csv a un paramètre encoding = "UTF-8", que vous pouvez utiliser.

Pour déboguer, je me suis appuyé sur des instructions d'impression. Je suis également intéressé de savoir si d'autres ont trouvé un moyen plus systématique.

4
maurice