# How to Build a CS2 Price Alert Bot

> A CS2 price alert bot can read the all-item `GET /v1/prices/latest` snapshot, select exact items or variants, and evaluate fresh marketplace asks or bids against stored rules.

The alert definition should name both the price field and source set. An ask-below alert watches acquisition listings; a bid-above alert watches an immediate-sale quote. These are different signals.

## Data inputs for price alerts

- Current `ask`, `bid`, `ask_volume`, and `bid_volume` fields across six marketplaces, with the source-specific exceptions documented below.
- `updated_at` and `collected_at` on each source row for freshness decisions.
- Supported phases and tiers under `variants`, with stable `version` codes and full variant names.
- Historical OHLC from December 24, 2025 for moving thresholds, high/low breakouts, or change calculations.

Current prices generally refresh every ~5-10 minutes. CSFloat bids refresh every ~10-30 minutes depending on liquidity. Polling more frequently than the underlying source cadence does not create a new observation.

## Mapping rules to the data

Fetch the current snapshot on a server, locate each rule by exact `market_hash_name`, and then choose the requested source and field. Compare `collected_at` with the snapshot's `response_time` to reject quotes older than the rule allows.

Keep alert state under the full item or variant identity plus source and field. This prevents a Phase 2 ask rule from sharing state with the base Doppler item or with a bid rule. For percentage changes, compare observations with known timestamps or use OHLC buckets instead of treating a long monitoring outage as one short-period move.

## Applicable endpoints

| Endpoint | Returns | Plans |
| --- | --- | --- |
| `GET /v1/prices/latest` | Current all-item quotes and variants | All plans |
| `POST /v1/prices/history` | Ask and bid OHLC at `5m` to `1d` intervals | Scale, Enterprise |

## Alert limits

- Skinport has no current bid. CSFloat and C5Game have no `bid_volume`, so rules requiring executable quantity cannot use those source rows.
- A current `ask` is one observed listing floor, not a completed sale or a reservation. It can disappear before the alert is acted on.
- Missing and null values should leave a rule unevaluated. Treating them as zero produces false price-drop alerts.
- A crossed bid and ask can reflect asynchronous observations. Discard the crossed pair for spread alerts instead of emitting a negative-spread event.

For sale-confirmed events, use the [price and sale-volume spike method](/resources/how-to-detect-cs2-price-volume-spikes) instead of current listing volume.
