Media proxy
The media proxy applies a saved media effect to an image on the fly. You configure an effect (halftone, dithering, …) in the console, and then point this endpoint at any image — it fetches the source, applies your effect server-side, and streams back the transformed image.
Url
https://improve.obelism.studio/media/:organizationId/:environment/:mediaEffectId
- Method:
GET organizationId- Unique identifier of the organization;org_XXXenvironment- environment to load;'develop' | 'staging' | 'production'mediaEffectId- Unique identifier of the effect config;media_XXX. You'll find it in the console on the effect's page (it's also in the page URL).
Query parameters
src- required. The source image to transform, URL-encoded. Its host must be in your Allowed origins for this environment (see Security).format- output format;'webp' | 'png' | 'jpeg'. Defaults towebp.w- maximum width in pixels. The image is scaled down to fit (never enlarged). Defaults to1600, capped at2048.q- output quality,1–100. Defaults to80. Ignored forpng.
Usage
Drop it straight into an <img> tag (remember to URL-encode src):
<img
src="https://improve.obelism.studio/media/org_XXX/production/media_XXX?src=https%3A%2F%2Fcdn.example.com%2Fphoto.jpg&w=800"
alt=""
/>Or request it directly:
curl "https://improve.obelism.studio/media/org_XXX/production/media_XXX?src=https%3A%2F%2Fcdn.example.com%2Fphoto.jpg&format=png"Security
This endpoint follows the same model as the rest of the API — client requests are validated by CORS against your Allowed origins, and server-to-server requests can pass an API token header.
In addition, the src image is protected against abuse:
- The source host must be one of your Allowed origins for the environment. The same allowlist that controls who may call the endpoint also controls which images may be proxied.
- Only
http/httpsURLs are accepted; private, loopback and link-local addresses are rejected.
If you get a 400 back, the most common cause is a src whose host isn't in your Allowed origins yet.
Caching
Transformed images are expensive to generate, so responses are sent with a long-lived Cache-Control and an ETag. Behind a CDN, each unique URL (effect + source + format/w/q) is generated once and then served from cache. Conditional requests with If-None-Match get a 304 Not Modified.
Because the response is keyed entirely by the URL, changing the effect config in the console produces a new ETag automatically — no manual cache busting needed.