API proxy

How to route the Purchasely API traffic through a proxy when api.purchasely.io is unreachable, for example in mainland China

Context

The SDK sends its API requests to api.purchasely.io. Some networks block that host. In mainland China, the Great Firewall blocks it, while the paywall host and the tracking host stay reachable. The API proxy gives the SDK a different base URL for the API host.

Purchasely operates a proxy at https://svc.purchasely.io. You can also host your own proxy.

🚧

SDK v6.1.0+ required

The proxy is available from v6.1.0 on iOS and on Android. It is not available on React Native, Flutter or Cordova.

What the proxy moves

Only the API host moves. The proxy never moves paywall.purchasely.io and tracking.purchasely.io. On iOS, these two hosts follow environment(_:), which targets production by default.

iOS

// The Purchasely proxy
Purchasely
    .apiKey("X-API-KEY")
    .proxy()
    .start()

// Your own proxy
Purchasely
    .apiKey("X-API-KEY")
    .proxy(api: URL(string: "https://proxy.example.com"))
    .start()

// No proxy: the SDK goes back to api.purchasely.io
Purchasely
    .apiKey("X-API-KEY")
    .proxy(api: nil)
    .start()

The parameter is a URL?. The no-argument form proxy() selects the Purchasely proxy. The nil value restores api.purchasely.io. A chain that calls neither form keeps the current setting.

Android

// The Purchasely proxy, or your own
Purchasely.Builder(applicationContext)
    .apiKey("X-API-KEY")
    .proxy(api = "https://svc.purchasely.io")
    .stores(listOf(GoogleStore()))
    .build()
    .start { error -> }

// No proxy: the SDK goes back to api.purchasely.io
Purchasely.Builder(applicationContext)
    .apiKey("X-API-KEY")
    .proxy(api = null)
    .stores(listOf(GoogleStore()))
    .build()
    .start { error -> }

The parameter is a String?. The null value restores api.purchasely.io, and it also clears a proxy that an earlier build() set. The Purchasely { } DSL provides the same method.

❗️

The no-argument form does the opposite on the two platforms

On iOS, proxy() selects the Purchasely proxy. On Android, proxy() restores api.purchasely.io, because the parameter has a default value of null. Always write the URL. The explicit form gives the same result on both platforms.

CalliOSAndroid
proxy()Selects https://svc.purchasely.ioRestores api.purchasely.io
proxy(api:) with a URLSelects that URLSelects that URL
proxy(api: nil) and proxy(api = null)Restores api.purchasely.ioRestores api.purchasely.io

URL rules

The SDK accepts a base URL that follows these rules:

  • The scheme is https. The SDK refuses http.
  • The URL carries a host.
  • The URL carries no query and no fragment.
  • The URL carries no credentials. Authenticate your own proxy with a header instead.

A path is valid. Both https://svc.purchasely.io and https://proxy.example.com/purchasely work. Write the URL with or without a trailing slash. Each SDK normalizes that character for its own network layer.

The SDK refuses any other value, writes an error log, and keeps the production host. The refusal never stops the initialization, so a wrong value never breaks the SDK.

The proxy belongs to the initialization

Both SDKs read the base URL when they build their network clients. They read it once. For this reason, the proxy is an option of the initialization chain, and neither platform provides a runtime setter.

Logs

The error log redacts the query, the fragment and the credentials of the refused URL, because the message must not carry a secret. The iOS SDK can also upload its logs to Purchasely for support. Read SDK diagnostics and observability for more information.


Did this page help you?