# Cache a Weather API for a Wix Velo Site

> Calling OpenWeather from Wix page code exposes the appid key and spends one call per visitor. A RealComposer pipeline keeps the key in the vault, caches results by location for ten minutes, and returns only temperature, condition, and icon for your Wix weather widget.

- Canonical page: https://realcomposer.com/recipes/cache-weather-api-wix-velo
- Client platform: Wix Velo
- Upstream services: OpenWeather
- Category: Edge Caching & Rate Limits
- JSON version: https://realcomposer.com/recipes/cache-weather-api-wix-velo.json
- Install in RealComposer (free plan, pre-fills this pipeline): https://realcomposer.com/dashboard/pipelines/new?recipe=cache-weather-api-wix-velo&via=agent

## Problem: Why weather widgets burn OpenWeather quota on Wix

Travel and venue sites on Wix often show current weather on every page view. Without a shared cache, popular pages make thousands of identical upstream calls, and the appid key placed in page code can be copied by anyone.

- OpenWeather appid exposed in Wix page code
- Free and paid call limits reached during traffic spikes
- Full forecast payloads sent for a three-field widget

## Solution steps

1. **Store credentials in Secret Vault**: Save OPENWEATHER_KEY in RealComposer so the value never enters the Wix Velo project.

2. **Configure the edge pipeline**: Add the upstream steps with vault header injection, set allowed origins, and map only the fields the screen binds.

3. **Render the weather widget in Velo**: Call your workspace edge URL with a restricted rc_live_ client token.

```
import { fetch } from 'wix-fetch';

$w.onReady(async () => {
  const res = await fetch('https://realcomposer.com/v1/workspace/cache-weather-api-wix-velo?lat=44.98&lon=-93.27', {
    headers: { Authorization: 'Bearer rc_live_client_token' },
  });
  const w = await res.json();
  $w('#tempText').text = `${Math.round(w.temp)}°`;
});
```

## Pipeline config

Import this config into a RealComposer pipeline. `{{secrets.NAME}}` values are read from the encrypted Secret Vault at request time, so the client never sees them.

```json
{
  "name": "Cache a Weather API for a Wix Velo Site",
  "method": "GET",
  "cacheTtlSeconds": 600,
  "authMode": "client_token",
  "steps": [
    {
      "stepKey": "weather",
      "upstreamUrlTemplate": "https://api.openweathermap.org/data/2.5/weather?lat={{query.lat}}&lon={{query.lon}}&units=imperial&appid={{secrets.OPENWEATHER_KEY}}",
      "httpMethod": "GET",
      "headersTemplate": {},
      "timeoutMs": 3000
    }
  ],
  "outputMapping": {
    "version": 1,
    "fields": [
      {
        "targetPath": "temp",
        "sourceStep": "weather",
        "sourcePath": "main.temp",
        "type": "number"
      },
      {
        "targetPath": "condition",
        "sourceStep": "weather",
        "sourcePath": "weather.0.main"
      },
      {
        "targetPath": "icon",
        "sourceStep": "weather",
        "sourcePath": "weather.0.icon"
      }
    ]
  }
}
```

## Call the pipeline

```bash
curl -X GET "https://realcomposer.com/v1/workspace/cache-weather-api-wix-velo" \
  -H "Authorization: Bearer rc_live_client_token"
```

## Payload before and after

Raw upstream response:

```json
{
  "coord": {
    "lon": -93.27,
    "lat": 44.98
  },
  "weather": [
    {
      "id": 800,
      "main": "Clear",
      "description": "clear sky",
      "icon": "01d"
    }
  ],
  "base": "stations",
  "main": {
    "temp": 41.2,
    "feels_like": 36.1,
    "pressure": 1021,
    "humidity": 58
  },
  "visibility": 10000,
  "wind": {
    "speed": 8.1,
    "deg": 300
  },
  "sys": {
    "country": "US",
    "sunrise": 1762952400,
    "sunset": 1762987200
  }
}
```

Slimmed RealComposer response:

```json
{
  "temp": 41.2,
  "condition": "Clear",
  "icon": "01d"
}
```

## FAQ

### How do I share cache entries across nearby visitors?

Round latitude and longitude to two decimals in page code before calling the pipeline, so visitors in the same area hit the same cache key.

### Can Wix backend code call the pipeline instead?

Yes. Calling from a backend web module also works and keeps the client token off the page, at the cost of an extra hop through Wix servers.
