Uh oh!
There was an error while loading. Please reload this page.
fix(security): base64-encode survey WebView payload to prevent script injection (ENG-1813) - #55
Conversation
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configurationConfiguration used: Organization UI Review profile: ASSERTIVE Plan: Pro Run ID: 📒 Files selected for processing (1)
Walkthrough
🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 inconclusive)
✅ Passed checks (4 passed)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
Uh oh!
There was an error while loading. Please reload this page.



What & why
ENG-1813 — script injection via the survey WebView payload.
The survey payload was spliced into a JavaScript template literal in the WebView HTML:
Survey content is server/admin-authored (headlines, subheaders, choice labels, styling, an HTML question type…). A value containing a backtick — or
${…}, which a template literal evaluates eagerly — breaks out of the string and runs as arbitrary JS in the WebView, which also holds theFormbricksJavascriptbridge. This is the Android counterpart of the iOS issue (formbricks/ios#51).The existing
#→%23and\"→'replacements were partial workarounds for the same class of problem: they did not stop backtick/${}breakout, and they corrupted legitimate survey content (every"became', and hex colors like#FF0000were percent-mangled).Fix
Mirror the iOS remediation — never let survey content be parsed as JS source:
Base64.NO_WRAP) and decode it in the WebView viaatob+TextDecoder, thenJSON.parse. Base64 output is[A-Za-z0-9+/=]only, so backticks,${…}, quotes and</script>can no longer appear in the string and break out.#→%23and\"→'workarounds — unnecessary once base64'd, and they were corrupting valid survey text (bonus data-integrity fix).loadDatacall toloadDataWithBaseURL(null, …)so the base64 (which may contain+,/,=) isn't mangled byloadData's data:-URL percent-decoding. This is the analogue of iOS'sloadHTMLString(_, baseURL: nil).Verification
./gradlew :android:compileReleaseKotlin— passes.FormbricksViewModelInstrumentedTest(getJson) is unaffected — its assertions don't depend on the removed workarounds.publishToMavenLocaland smoke-tested in a host app — surveys render correctly.Notes / scope
${}/</script>) through payload generation and asserts it appears only inside the base64 blob and round-trips intact.