Environments

Two environments, Test and Production. Which one you reach is decided by a single address: the one you load the widget from.

Saphere runs two environments. They are completely separate: separate accounts, separate API keys, separate data. A measurement made in Test never shows up in Production, and a key issued for one is refused by the other.

EnvironmentWhat it is forCDNAPI
ProductionReal measurements, real quota. What your users reach.https://cdn.saphere.aihttps://api.saphere.ai
TestIntegration, acceptance, and validation of what comes next. Sometimes slightly ahead of Production.https://cdn.test.saphere.aihttps://api.test.saphere.ai

Choosing an environment means choosing an address

There is no setting to change. You reach an environment through the address you call, and the widget follows it.

<!-- Test -->
<script type="module">
    import SaphereScan from "https://cdn.test.saphere.ai/saphere-scan/v2/main.js"
</script>

<!-- Production -->
<script type="module">
    import SaphereScan from "https://cdn.saphere.ai/saphere-scan/v2/main.js"
</script>

That single line settles the rest. The widget works out the address of the measurement service from the CDN it was loaded from. Code served by cdn.test.saphere.ai talks to api-measure.test.saphere.ai, and never to Production. There is nothing else to switch, and therefore nothing that can be left half-switched.

One thing does not follow on its own

Your own token endpoint. If the widget loads from the Test CDN, your server has to call the Test API to issue the access token. A Production token presented to the Test service is refused, and the measurement never starts.

Read the environment from your own configuration. Never write one address into the code.

What differs, and what does not

TestProduction
API keysIssued for Test onlyIssued for Production only
Accounts, measurements, tokensSeparate dataSeparate data
Version servedSometimes aheadThe released version
Routes, event names, optionsThe released contract, sometimes plus what is being validatedThe released contract

Test is also where new developments are validated before release. It is therefore sometimes slightly ahead of Production: a screen, an option or an event may exist there before it exists in Production. The gap is small and it closes with the next release, but it is real, and it runs in the direction you would expect — Test first, Production after.

Two practical consequences.

Build against what is documented, not against what you observe on Test. Something you find there and that this documentation does not describe may be under validation. It is not a contract yet.

A behaviour that works on Test and not in Production is worth a question rather than a workaround. It is usually a feature that has not been released yet, and the answer is a date rather than a change to your code.

Moving an integration to Production

  1. Change the CDN address in your page or in your app.
  2. Point your token endpoint at the Production API, and give it the Production API key.
  3. Check that the key never reaches the browser. Access tokens explains how.

Nothing else changes on your side: no option to rename, no event to rewire, no response shape to adapt.

Never send a Production API key to a page

A Production API key never expires and opens every route of your account. Placed in a page, anyone who opens the browser’s developer tools can read it. Revoking it means replacing it, which cuts off every one of your integrations at the same moment.

This is why the unsafe-api-key strategy carries that name, and why it belongs to trials on Test only.