Feed shiny text input into python chunk

rmarkdown
reticulate
flexdashboard

#1

I've tried to look into some examples but I still haven't quite grokked this, or know if it's possible to do.

I'm running shiny in an Rmd flexdashboard file.

What I'd like to be able to do is take the text box input and feed it into a successive python chunk.

My problem is that I don't know how to just capture the value of the text input and use it outside of the reactive environment, if that makes sense.


# input object = text area box

textAreaInput("text", label = h3("Paste Abstract Here"), width = '600px', height = '300px')

# and the submit button

actionButton("submit", "Submit")

# this is the variable I create so that I can renderText, use it with an action button, etc.

v <- reactiveValues()

# which populates if the submit button is clicked

observeEvent(
  input$submit,
  v$data <- input$text
)

# and I'd like to be able to do something like this:

var <- value of v$data/input$text
# successive python chunk
test = str(var) 

#2

You're on the right track, reactivity is what you need. I don't know about passing the value to a python snippet but here's a really good tutorial on reactivity. Should give you everything you need (minus the python bit but I'd start with the reactivity).


#3

I'm fine running this without the python component - I can take the input, create various outputs, etc., and run it in Shiny ...the important component that I'm missing is taking the value of the input$text and turning it into a variable that I can use in the successive python chunk. And maybe I'm missing it - I've gone through that tutorial before, and I'm couldn't find a solution to this particular problem.


#4

Hopefully this'll be close to your goal.

The first hurdle is passing the text from R to Python. For this, the reticulate package is great. The second hurdle was the one you seem to care about, which is having a reactive chunk.

I approached it in a round-about way: instead of a reactive chunk, have knitr convert a character vector "chunk" to HTML within a reactive context. Then feed that HTML to renderUI.

---
title: "Untitled"
output: 
  flexdashboard::flex_dashboard:
    orientation: columns
    vertical_layout: fill
runtime: shiny
---

```{r setup, include=FALSE}
library(shiny)
library(flexdashboard)
library(knitr)
library(reticulate)
```

Column {data-width=650}
-----------------------------------------------------------------------

### Chart A

```{r, e}
textAreaInput("text", label = h3("Paste Abstract Here"), width = '600px', height = '300px')
actionButton("submit", "Submit")
v <- reactiveValues()
renderUI(v[["py_chunk"]])

observeEvent(
  input$submit,
  {
    var <- input$text
    # Each chunk line is an element of the vector
    py_code <- c(
      "```{python}",
      "test = str(r.var)",
      "print(test)",
      "```"
    )
    # Make sure knitr's converting to HTML
    knitr::render_html()
    # Then store the output in the reactive value
    v[["py_chunk"]] <- HTML(knitr::knit(text = py_code))
  }
)
```

Hopefully it works for you. R is calling Python, so the OS environment comes into play. I had trouble with bit-mismatches between R and Python at first, but then it stopped, which worries me all the more.


#5

Thank you! I would not have thought of anything like this. I'm trying to run it and am getting an error about highr, so I'll have to take a closer look at it - will update and mark solved tomorrow!


#6

I was getting messages about highr, too. If you figure out how to appease knitr for that, please share.


#7

Ok! I got it to work just by commenting out the line here:

knitr::render_html()

I'm not sure what the issue is, though, that this solves.

Your script prints the entire py_code chunk, and I'm not sure how to utilize this the way I need to afterward, but that's more creative coding for me to solve, haha. Thanks very much!