surveydown-dev / demo-external-redirect

A demo survey showcasing redirection to external links for survey panels
0 stars 0 forks source link

Storing the URL parameters in the data using sd_store_value? #1

Open willking98 opened 3 weeks ago

willking98 commented 3 weeks ago

Is it possible to store the url parameters collected using sd_get_url_pars() in the csv/supabase data output?

Thanks, Will

jhelvy commented 3 weeks ago

You should be able to using the sd_store_value() function. This might work:

sd_store_value(sd_get_url_pars(), id = "url_pars")

The id argument is the name of the column that will appear in your data.

The sd_get_url_pars() must be called inside a reactive context, and it will return a list of all of the url parameters present. But I think this will work because sd_store_value() calls shiny::isolate(). When you store an object like a list, it just concatenates the list into a single character separated by commas.

So let's say you had a url like this:

website.com/?resp_id=123?survey_id=456

Then the resulting value in the url_pars column should be (I think) "123, 456", where the parameter names get dropped and only the values are stored.

This may not be ideal, so I think you could perhaps adjust this to store each individual url parameter by specifying which url parameter you want to get from sd_get_url_pars(). So maybe something like this:

sd_store_value(sd_get_url_pars("resp_id"), id = "resp_id")
sd_store_value(sd_get_url_pars("survey_id"), id = "survey_id")

Then you should get two columns: the resp_id column would store 123, and the survey_id column would store 456.

I haven't tested this, so give it a try and let me know if it works. If it does, I can update the documentation to explain this.

willking98 commented 3 weeks ago

I'm struggling to get this to work. I've tried to adapt the survey.qmd redirect demo code to get this to work but unfortunately I am unable to get the sd_store_value function to successfully store the data.

jhelvy commented 3 weeks ago

Okay I realized why this wasn't working. It was because the sd_get_url_pars() function was not a reactive expression, so you had to put it inside a call to reactive(). I've now modified this so that the function now returns an evaluated reactive expression, so try reinstalling it and I believe the same code I wrote above should work.

remotes::install_github("surveydown-dev/surveydown", force = TRUE)
jhelvy commented 3 weeks ago

Also in the future, would you mind posting issues like this either in the main surveydown repo or the discussions? That will make it easier for others to find if they have a similar issue.

willking98 commented 3 weeks ago

Thanks for that John, the sd_store_value function works now. Though I think the latest update might have done something funky with my survey. I've made quite a messy Best-Worst Scaling (Max-Diff) survey that was working pretty nicely earlier on. For one reason or another this no longer works since the update. This could be that I have messed with something and have broken it myself around the time of the update or this could be a broader issue.

I have reverted back to a previous version of the survey that I committed about a week ago and I am experiencing the same issue. My specific issue is that sd_output('cbc_q1_w_tired') is not rendering in the survey. FYI cbc_q1_w questions are conditional upon a show_if.

# Question 1
::: {style="width:600px; margin: 0 auto;"}
```{r}
sd_output('cbc_q1', type = 'question')

sd_output('cbc_q1_w_tired', type = 'question')
sd_output('cbc_q1_w_walking', type = 'question')
sd_output('cbc_q1_w_sports', type = 'question')
sd_output('cbc_q1_w_concentration', type = 'question')
sd_output('cbc_q1_w_embarrassed', type = 'question')
sd_output('cbc_q1_w_unhappiness', type = 'question')
sd_output('cbc_q1_w_treated', type = 'question')

I will share my repository here. Apologies for the very messy and repetitive code in the server.R file.

Also, I will make sure to post any future queries to main surveydown repo! Thanks a lot for your help.

jhelvy commented 3 weeks ago

Wow that's a pretty complex survey! Glad to see people really heavily testing out our package :)

I noticed that your call to sd_database() is in the server.R file, that should instead be in the setup code chunk. We realized this in another issue and [updated the docs](remotes::install_github("surveydown-dev/surveydown", force = TRUE)) accordingly. The db object should still be accessible in the server code chunk if it is defined in the setup chunk.

While I'm not able to immediately trouble shoot the issue, I will give you a heads up that we're soon going to be releasing a rather substantial update to the architecture of the platform, mostly due to security issues. Short story is it will be two files now: survey.qmd and app.R. The survey.qmd file will still define all the survey content, and the app.R file will define a rather traditional shiny app with a ui and server. So you will just copy over the code in your server code chunk to the server function in app.R. Not too much more changes. But this results in better overall performance and also a much more secure app.

willking98 commented 3 weeks ago

I had originally had the sd_database() function in the setup code chunk but I kep getting the error shown below. I moved the chunk to the server function and things worked smoothly.

Warning: Error in eval: object 'db' not found
  49: sd_get_data
  48: eval
  47: eval
  45: source
  42: server
   5: <Anonymous>
   3: rmarkdown::run
   2: run
   1: .main
Error in eval(ei, envir) : object 'db' not found

I just moved this and rerun it and received the same error. Is it possible for me to revert back to surveydown 0.2.3 locally and rerun to check that it definitely was the update that is causing the issues for me? Best case scenario I just have a typo somewhere that is unrelated to the update.

Thanks, Will

willking98 commented 3 weeks ago

Also you can see what a version of the survey is supposed to look like when functional here

jhelvy commented 3 weeks ago

I had originally had the sd_database() function in the setup code chunk but I kep getting the error shown below.

I've seen this too when I have a two-file structure the way you have yours set up with a separate server.R file. I believe that is the issue, but it is puzzling as it shouldn't matter. In any case, in the coming architecture this will be defined in an app.R file, not the survey.qmd file, which will solve this issue. Still working on it, perhaps another week or so until we release.

willking98 commented 3 weeks ago

Thanks for the update on that. The other issue I have been having since the latest update is this error in response to these two lines of code. I would imagine that this is connected in some way to the lack of rendering issue.

data <- sd_get_data(db)
respIDs <- unique(data$respID)

Warning: Error in $: object of type 'closure' is not subsettable
  50: <Anonymous>
  49: unique
  48: eval
  47: eval
  45: source
  42: server
   5: <Anonymous>
   3: rmarkdown::run
   2: run
   1: .main
Error in data$respID : object of type 'closure' is not subsettable

I'll do some more thorough troubleshooting in the morning and try and figure out what the issue is. I look forward to the new architecture!

Thanks for the help!

Will

jhelvy commented 3 weeks ago

I believe these are probably related. If you want to preview what the new design will look like, take a look at the dev branch of the documentation website. You can clone that, open the .Rproj file, then run quarto preview in the terminal and you'll see a local version of the site. The "Survey Components" page has a good overview of the structure. We're still working on the site and package so we can release everything at once.

willking98 commented 3 weeks ago

I've had a good look at that. I won't bother trying to solve the issues I'm having without waiting for the new architecture to be released.

jhelvy commented 2 weeks ago

Just released the new version (see this discussion)

willking98 commented 2 weeks ago

Thanks for the update on that. The other issue I have been having since the latest update is this error in response to these two lines of code. I would imagine that this is connected in some way to the lack of rendering issue.

data <- sd_get_data(db)
respIDs <- unique(data$respID)

Warning: Error in $: object of type 'closure' is not subsettable
  50: <Anonymous>
  49: unique
  48: eval
  47: eval
  45: source
  42: server
   5: <Anonymous>
   3: rmarkdown::run
   2: run
   1: .main
Error in data$respID : object of type 'closure' is not subsettable

I'll do some more thorough troubleshooting in the morning and try and figure out what the issue is. I look forward to the new architecture!

Thanks for the help!

Will

I'm still receiving the same issue as before the update with sd_get_data() returning an object of class "reactiveExpr" "reactive" "function". For context I am trying to solve the assignment problem to prevent duplicate respIDs. Code available here.

UPDATE: This is now working fine provided the sd_get_data() function is used outside of the server function but inside the app.R.

jhelvy commented 2 weeks ago

Just took a look. One thing I noticed is you still have ignore = TRUE in the sd_database() call, which means the database won't make a connection. You have to remove that and you should see a message that the database connection is successful or not.

Second, you have data <- sd_get_data(db) outside of the server() function, which means it will be a static call to the database only once when the app launches and the same for all sessions. You should put that down into the server() function for it to be called on each session.

Finally, the way we had this set up was that when you call sd_get_data() inside the server(), it always returned a reactive expression, which could only be used inside another reactive context. For example, you would have to do something like this:

data <- sd_get_data(db)
respIDs <- reactive({ data()$respID })

But then the respIDs() would also be a reactive expression, which isn't what you want.

For your use case, you just need a one-time copy of the data at the time the session launches. So I just modified the sd_get_data() function so that the user can control this. Reinstall the latest from github and it should work. Now if you want the data to be returned as a reactive expression that continuously updates, you have to set the refresh_interval argument to a positive number (the refresh interval in seconds).