I want to put a captcha in my shiny app. I used ShinyFriendlyCaptcha package. This is my MWE. It shows only the captcha. It works well:
library(shiny)
library(ShinyFriendlyCaptcha)#devtools::install_github("mhanf/ShinyFriendlyCaptcha")
# UI
ui<-fluidPage(
sfc_output(
id = "test",
sitekey = 'FCMLPPDE8H8IO645',
lang = "en",
dark_mode = FALSE,
eu_endpoint = FALSE,
theme_bs5 = TRUE
)
)
# Server
server <- function(input, output) {
# shinyvalidate
# captcha response
captcha_result <- sfc_server(
id = "test",
secret = 'A1T24PTUO6EU091S3HVJC3FRN5UE3JPBQ6UDO3RI3R5NM3VE4J6AQ0A8HC',
sitekey = 'FCMLPPDE8H8IO645',
eu_endpoint = FALSE
)
}
# Run the application
shinyApp(ui = ui, server = server)
Now, I need to build the UI dynamically:
library(shiny)
library(ShinyFriendlyCaptcha)#devtools::install_github("mhanf/ShinyFriendlyCaptcha")
ui<-uiOutput("body")
# Server
server <- function(input, output) {
# captcha response
captcha_result <- sfc_server(
id = "test",
secret = 'A1T24PTUO6EU091S3HVJC3FRN5UE3JPBQ6UDO3RI3R5NM3VE4J6AQ0A8HC',
sitekey = 'FCMLPPDE8H8IO645',
eu_endpoint = FALSE
)
output$body <- renderUI({
fluidPage(
sfc_output(
id = "test",
sitekey = 'FCMLPPDE8H8IO645',
lang = "en",
dark_mode = FALSE,
eu_endpoint = FALSE,
theme_bs5 = TRUE
)
)
})
}
# Run the application
shinyApp(ui = ui, server = server)
This code does not show anything (the app does not fail), and this message appears in the console:
Listening on http://127.0.0.1:5396
Input to asJSON(keep_vec_names=TRUE) is a named vector. In a future version of jsonlite, this option will not be supported, and named vectors will be translated into arrays instead of objects. If you want JSON object output, please use a named list instead. See ?toJSON.
I found a similar question here, but it does not help. Any idea how to solve it?
The problem is that
ShinyFriendlyCaptcha::sfc_outputloads some JavaScript which fires whendocument.readyStatedoes not equalloadinganymore. With a dynamic UI, this state is achieved before you try to add your captcha (basically once the static UI is loaded).Thus, all the setup code won't run, because the JS looks for the appropriate div which it cannot find.
You see that the JavaScript is executed too early if you open the developer console:
With the way how
sfc_outputis currently implemented, I guess you have no luck using it dynamically.A crude workaround would be to split the HTML and the JS dependencies and use
insertUIto insert them one after the other:Then you can use
sfc_output2like this: