Get SQL code from SQL chunk with variables evaluated

Is it possible to get the SQL code from a SQL chunk in rmarkdown, with the variables (?myvar) and parameters (@myparam) evaluated? See the following example, adapted from Rmd file with embedded SQL chunk. Possible to move the SQL to external file then source? - #3 by cderv

---
title: "Get SQL with evaluated variables from SQL chunks"
output: html_document
---
  
In order to provide a reproducible example, we use dplyr and dbplyr with `tbl_memdb` to load a table into a memory db.

```{r}
library(dplyr)
library(dbplyr)
iris_db <- tbl_memdb(iris)
# we isolate the connection object 
con <- src_memdb()$con
species <- "setosa"
```

We check that it works with SQL chunk to filter data into an R object

```{sql, connection=con, output.var="iris_subset"}
SELECT * FROM iris WHERE Species = ?species
```

Now I would like to get the SQL command above, with the `species` variable evaluated, i.e.

```sql
SELECT * FROM iris WHERE Species = 'setosa'
```

Or what I would get from 

```{r}
glue::glue_sql("SELECT * FROM iris WHERE Species = {species}")
```

I tried the `cat` engine like so

```{cat, engine.opts = list(file = "iris_subset.sql", lang = "sql")}
SELECT * FROM iris WHERE Species = ?species
```

but it writes `?species` as is and its value. 

I am not sure what is the desired output.

You want to have the ?species replace in the output code chunk while the chunk still be evaluated ?

What is the desired result ? Also you mention @myparam. Can you illustrate ?

glue_sqlis working right ?

When I have a chunk like this

```{sql, connection=con, output.var="iris_subset"}
SELECT * FROM iris WHERE Species = ?species
```

I would like to get this SQL string back (i.e. the string should contain 'setosa', not ?species):

SELECT * FROM iris WHERE Species = 'setosa'

I'd like to see the actual SQL command that is sent to the DB.

glue_sql() is working right, but I would have to convert all ?myvars to {myvars} (and handle ids and string literals and so forth).

This feature does not exist yet, it would need to be added into knitr, maybe using a chunk option.

Can you open a feature request into knitr repo ? Thanks !

Sorry, this took a bit

Thanks!

I was just looking into it and posting an answer.

You can in fact use sql.show_interpolated = TRUE to do this I think

---
title: "Get SQL with evaluated variables from SQL chunks"
output: html_document
---
  
In order to provide a reproducible example, we use dplyr and dbplyr with `tbl_memdb` to load a table into a memory db.

```{r}
library(dplyr)
library(dbplyr)
iris_db <- tbl_memdb(iris)
# we isolate the connection object 
con <- src_memdb()$con
species <- "setosa"
```

We check that it works with SQL chunk to filter data into an R object

```{sql, connection=con, output.var="iris_subset", sql.show_interpolated = TRUE}
SELECT * FROM iris WHERE Species = ?species
```

```{r}
head(iris_subset)
```

Is this what you expect ?

2 Likes

On rOpenSci's slack channel, Jenny Bryan pointed me at {glue}'s glue_sql engine. This is indeed somewhat easier to debug, because I can just copy paste the code from the glue_sqlchunk into the glue::glue_sql() function. However, if the code contains quotation marks (i.e. quoting DB object names or strings in the SQL code) then I'd have to escape those quotes before.

In principle yes. Does it work without knitting the (whole) document successfully / actually sending the SQL code to the DB?

I guess my main use-case is when I need to debug my SQL code (variables quoted correctly? correct values? etc.). And the document wouldn't knit successfully, if the SQL code is not working correctly, I suppose?
(Sorry, I guess I wasn't aware of all requirements when I posted this initially.)

I suppose it does, when setting the chunk option error=TRUE.

Is there also a sql chunk option for "don't send this query to the DB"?
Where is sql.show_interpolated (and others?) documented?

:man_facepalming: I think what I want is eval=FALSE, of course (and then error does not matter).

eval = FALSE should not eval the chunk so not send to db.

Options are usually documented here: Options - Chunk options and package options - Yihui Xie | 谢益辉
But for specific engine, it seems not all are documented (except in knitr NEWS file).

For this one, I'll probably add a recipe in R Markdown Cookbook

1 Like

This topic was automatically closed 7 days after the last reply. New replies are no longer allowed.

If you have a query related to it or one of the replies, start a new topic and refer back with a link.