Why you need this
When you initializePortal, the SDK creates a hidden iframe served from Portal’s servers (web.portalhq.io by default). Everything sensitive is scoped to that iframe’s origin: the Client Session Token cookie that authenticates your user, and the user’s MPC signing share in LocalStorage. Your application’s JavaScript cannot read either, which protects the signing share from XSS bugs in your app.
Browsers treat cookies and storage that belong to a different site than the one in the address bar as third-party. Safari blocks third-party cookies by default, Firefox partitions them, and Chrome blocks them in Incognito. When they are blocked, the iframe cannot keep its session or its signing share, and wallet operations fail.
A custom subdomain fixes this: point portal.yourdomain.com at Portal, and the SDK loads the iframe from that subdomain. Same Portal servers, but now first-party in every browser. The iframe is still a different origin than your app, so the signing share stays isolated.
Setup instructions
1. Create the DNS record
Create aCNAME record in your DNS provider:
- Set the DNS Record Type to
CNAME. - Set the Name or Host field to
portal(or any subdomain name you prefer). This creates a subdomain likeportal.yourdomain.com. - Set the Data or Content field to
web.portalhq.io.
Your subdomain must be a child of the domain your application runs on. If your application is at
yourdomain.com, configure portal.yourdomain.com. If your application is at app.yourdomain.com, configure portal.app.yourdomain.com. The browser only treats the iframe as first-party when the subdomain and your application share a site.2. Verify the record
Confirm the record resolves before contacting Portal:web.portalhq.io:
3. Tell Portal your subdomain
Reach out to Portal with the subdomain value. Portal updates its backend to accept traffic on your subdomain and issues a TLS certificate for it.Until the certificate is issued, requests to your subdomain fail with a TLS error. This is expected. Certificate issuance completes shortly after your CNAME resolves and Portal finishes the configuration. Portal will confirm when your subdomain is ready.
4. Set the host in your SDK config
Pass your subdomain as the host when you initialize Portal. Without this step, the SDK keeps using web.portalhq.io and nothing changes.
5. Verify end to end
Open your application in Safari (it blocks third-party cookies by default, so it is the strictest test) and run a wallet operation like generate or sign. If it succeeds in Safari, the subdomain is configured correctly.Security in depth
Running the Web SDK on a separate subdomain keeps Portal’s resources isolated from your main application. Cookies The Web SDK uses a cookie to store theClientSessionToken, which authenticates a user to the Portal backend.
The cookie is configured with the http-only and secure flags, so it is only transmitted over TLS and is inaccessible to JavaScript.
The cookie is scoped to the subdomain, which means it is not included on requests to your application, only on requests to Portal’s backend.
LocalStorage
The Web SDK uses LocalStorage to store the user’s signing share, which is used during MPC operations to sign messages and transactions.
Values in LocalStorage are scoped to the subdomain, so they cannot be accessed by your application’s JavaScript. This isolation protects the MPC share from XSS bugs or malicious scripts on your web application.
Troubleshooting
- Works in Chrome but not Safari: the
hostoption is probably not set, so the SDK still loads the iframe fromweb.portalhq.io. Check step 4. - TLS or certificate error on the subdomain: the certificate has not been issued yet, or the CNAME changed after issuance. Verify the record with
digand confirm the subdomain with Portal. digshows no CNAME: the record has not propagated, or it was created on a different zone than your application’s domain.