Web SDK troubleshooting
This page covers common Web SDK integration failures related to
SharedArrayBuffer, COOP/COEP, Safari/iOS, third-party scripts, iframe
embedding, and Android WebView.
Refer first to system requirements for the baseline browser and header requirements. This page addresses cases where integration still fails after the baseline setup has been applied.
If the Web SDK reports that the browser is not compatible, the most common cause is incomplete cross-origin isolation rather than the SDK bundle itself. A single response containing some expected headers is not sufficient.
Verify the deployed responses first
Before browser-specific or framework-specific debugging begins, the failing deployment should be verified directly:
window.crossOriginIsolatedevaluates totrue.- The main document response includes
Cross-Origin-Opener-Policy: same-origin. - The main document response includes
Cross-Origin-Embedder-Policy: require-corp. - The SDK script /
.mjs, worker bundle, and every.wasmresponse are served with the expected headers. - For iframe setups, both the parent response and the iframe response are
configured correctly, and the iframe includes
allow="cross-origin-isolated". - After header changes, validation is repeated with a hard refresh and in Incognito or a fresh browser profile so cached responses do not hide partial rollout issues.
Several framework dev servers inject COOP/COEP only for local development.
The deployed responses should therefore be verified directly rather than
inferred from local-development behavior.
Browser reports incompatibility or SharedArrayBuffer is not supported...
This usually indicates that the page is not cross-origin isolated.
Verification points:
- The SDK script /
.mjs, worker bundle, and.wasmresponses are loaded from the expected origin and are not missing headers because of a different host, proxy, or CDN rule. - If the SDK is embedded in an iframe, the iframe document is also isolated and
the iframe includes
allow="cross-origin-isolated".
Recommended changes:
- The actual deployed responses should be configured, not only the local dev server.
- The configuration should be applied consistently to the main document and every SDK-owned response.
- After changes, validation should be repeated with a hard refresh and in Incognito or a fresh browser profile.
- If the page also loads third-party widgets, the scan flow should generally be
moved to a dedicated route or subdomain unless those resources are known to
be
COEPcompatible.
If the browser still lacks required features after the page is isolated, check the supported browser list on the system requirements page.
Chrome works, but iPhone / Safari fails
The most common cause is relying on
Cross-Origin-Embedder-Policy: credentialless as a workaround for
third-party resources. That can appear to help in Chromium-based browsers, but
it is not a reliable configuration when Safari/iOS support is required.
Verification points:
- Safari / iOS is on a supported version.
- The failing environment is not using
Cross-Origin-Embedder-Policy: credentialless. - All resources on the isolated page are compatible with
COEP/CORS/CORP.
Recommended changes:
Cross-Origin-Embedder-Policy: require-corpshould be used.- The page and all SDK-related resources should be made compatible with that setup.
- Incompatible third-party scripts should be removed from the scan route rather
than treating
credentiallessas a long-term fix.
Normal sessions work, but Incognito or first load fails
This is usually a caching or partial-rollout problem rather than a browser issue.
Typical causes:
- The main page has the new headers, but the cached worker or
.wasmfile does not. - Different CDN or reverse-proxy rules apply to HTML, scripts, and binary assets.
- A previous successful session masked the problem until a fresh profile retrieved the missing responses again.
Verification points:
- A hard refresh is performed after every header change.
- Validation is repeated in Incognito or a fresh browser profile.
- The actual network responses for the main document, SDK script /
.mjs, worker bundle, and.wasmare inspected.
Recommended changes:
- CDN caches should be purged if needed.
- Header rules should be updated for every response type involved in the SDK flow.
- A cached successful session should not be treated as proof that the configuration is correct.
Third-party scripts stopped working after enabling COOP/COEP
This is a common integration outcome and not a Shen.AI-specific bug. The Web
SDK requires cross-origin isolation because it uses SharedArrayBuffer, which
changes what the page is allowed to load.
Typical symptoms:
- analytics, chat, session replay, payment, or SSO widgets stop rendering
- browser errors such as
ERR_BLOCKED_BY_RESPONSE.NotSameOriginAfterDefaultedToSameOriginByCoep - the SDK works on a bare test page but not on the production shell
Recommended changes:
- The scan flow should be placed on a dedicated route or subdomain.
crossorigin="anonymous"should be added when the vendor explicitly supports CORS for that resource.- Vendors should return compatible
Access-Control-Allow-Originand/orCross-Origin-Resource-Policyheaders. - Proxying the resource under the same origin should be treated as a last resort.
If Safari/iOS support matters, do not switch the whole setup to
credentialless just to keep incompatible vendors working in Chromium.
Iframe embedding fails even though the iframe page has headers
For cross-domain iframe setups, the iframe page alone is not enough.
Verification points:
- The parent document has
COOPandCOEP. - The iframe document has
COOPandCOEP. - The iframe element includes
allow="cross-origin-isolated". - The SDK script /
.mjs, worker bundle, and.wasmloaded inside the iframe are served consistently. - The iframe context reports
window.crossOriginIsolated === true.
Recommended changes:
- Both the parent page and the iframe page should be isolated.
credentiallessshould not be relied on when Safari/iOS support is required.- If the parent page cannot be isolated because of incompatible third-party content, the scan flow should be moved to a dedicated top-level route or subdomain.
Android WebView support
No. Android WebView is not supported because the Web SDK requires
SharedArrayBuffer and cross-origin isolation.
Supported alternatives:
- Chrome Custom Tabs
- a full browser page
- the native Android SDK
When the Web SDK is tested inside Android WebView, the failure should not be treated as a missing-header problem. The environment itself is unsupported.
Scoping isolation to the scan route or subdomain
Scoping isolation only to the scan route or subdomain is usually the preferred
mitigation when the rest of the site depends on third-party resources that are
not COEP compatible.
Recommended pattern:
- Only the route or subdomain that hosts the scan experience is isolated.
- The isolated page itself, plus the SDK script /
.mjs, worker bundle,.wasm, and any iframe document it uses, all receive the correct headers. - Unrelated marketing, checkout, or support pages remain outside the isolated shell if they depend on incompatible third-party integrations.
If the scan route is embedded in an iframe, both the parent page and the iframe page still need to be isolated.
Framework-specific header examples
These examples show where to inject the required headers for common stacks. The
mechanics differ by framework, and the examples are intentionally not
identical: static hosting examples often include
Cross-Origin-Resource-Policy, while local dev-server examples frequently only
inject COOP/COEP because they serve same-origin assets locally.
- Static hosting / local static server:
examples/web/js-minimal/serve.json
adds
COOP,COEP, andCORPto all routes. This is the closest example in the public examples repo to a production-style static-host setup. - React with Vite:
examples/web/react-vite/vite.config.ts
injects
COOPandCOEPthroughserver.headersfor local development. Production still needs equivalent behavior at the deployed server or CDN. - Vue with Vite:
examples/web/vue-vite/vite.config.ts
does the same through Vite’s
server.headersconfiguration. - Angular dev server:
examples/web/angular/angular.json
adds
COOPandCOEPunderserve.options.headersfor local development. Production deployments must configure the deployed responses separately.
Read more about COOP and COEP at
web.dev/coop-coep .