Summit 26 from June 1-4 in San Francisco

Lead your organization in the era of agents and enterprise intelligence.

Snowflake for DevelopersGuidesCortex REST API Usage Visualization
Quickstart

Cortex REST API Usage Visualization

Cortex LLM
Priya Joseph

Overview

Duration: 2

This quickstart shows how to build a self-contained HTML dashboard that visualizes your Cortex REST API token consumption using the Canvas API — with zero external CDN dependencies. The dashboard reimplements five chart types commonly built with Vega-Lite, using only native browser APIs.

What You'll Learn

  • How to query SNOWFLAKE.ACCOUNT_USAGE.CORTEX_REST_API_USAGE_HISTORY for token-level data
  • How to build interactive charts with the HTML Canvas API (no libraries)
  • Five visualization patterns: scatter, histogram, circle plot, trellis dot plot, and multi-line cumulative
  • How to implement tooltips and retina-display support with devicePixelRatio

What You'll Need

  • A Snowflake account with Cortex REST API access
  • ACCOUNTADMIN role or appropriate privileges to query ACCOUNT_USAGE views
  • A modern web browser (Chrome, Firefox, Safari, Edge)
  • A text editor

What You'll Build

A five-chart dashboard showing:

  • Token Scatter — each API call as a sized dot (√ scale)
  • Token Distribution Histogram — stacked bars by model and token range
  • Circle Plot — bubble matrix of request volume by date and model
  • Trellis Dot Plot — faceted strip plot of per-request tokens
  • Interactive Multi-Line — cumulative token usage over time with cross-model hover tooltip
Dashboard Overview

Query Your Usage Data

Duration: 3

The dashboard is powered by SNOWFLAKE.ACCOUNT_USAGE.CORTEX_REST_API_USAGE_HISTORY. Run the following SQL to extract per-request token data:

USE ROLE ACCOUNTADMIN;
GRANT IMPORTED PRIVILEGES ON DATABASE SNOWFLAKE TO ROLE <your_role>;

SELECT
    DATE_TRUNC('day', START_TIMESTAMP)::DATE  AS date,
    TO_CHAR(START_TIMESTAMP, 'HH24:00')       AS hour,
    MODEL                                      AS model,
    TOKEN_COUNT                                AS tokens,
    LEFT(REQUEST_ID, 8)                        AS id
FROM SNOWFLAKE.ACCOUNT_USAGE.CORTEX_REST_API_USAGE_HISTORY
WHERE START_TIMESTAMP >= DATEADD('day', -30, CURRENT_TIMESTAMP())
ORDER BY START_TIMESTAMP;

Copy the output into a JSON array in the format:

[
  {"date":"2026-03-13","hour":"03:00","model":"claude-sonnet-4-5","tokens":19757,"id":"92b20b48"},
  ...
]

Tip: The ACCOUNT_USAGE views have up to 2 hours of latency. For near-real-time data, use INFORMATION_SCHEMA.CORTEX_REST_API_USAGE_HISTORY (15-minute latency, shorter retention).

Dashboard Architecture

Duration: 3

The dashboard is a single HTML file with no external dependencies — no Vega-Lite, D3, or Chart.js CDN imports. All rendering is done with the Canvas 2D API.

Key Design Patterns

PatternImplementation
Retina supportdevicePixelRatio scaling on every canvas
LayoutCSS Grid (2-column) with full-width bottom chart
Color schemeDark theme (#0f1724 bg, #1a2332 cards, #29b5e8 accent)
TooltipsFixed-position <div> shown on mousemove, hidden on mouseleave
Scale typesLinear and √ (square root) for token values
Hit testingMath.hypot() for circles, bounding-box for rectangles

File Structure

cortex-rest-api-usage-visualization/
├── cortex_rest_api_dashboard.html   ← the complete dashboard
├── assets/
│   ├── ScatterStackedDensity.png
│   ├── CirclesTrellis.png
│   └── Interactive.png
└── cortex-rest-api-usage-visualization.md

Chart 1 — Token Scatter Plot

Duration: 3

The scatter plot renders each Cortex REST API call as a circle. The y-axis uses a square root scale so both small (< 500) and large (∼ 20K) token values are visible without the small values collapsing to the axis.

Scatter and Histogram

How the √ Scale Works

const sqrtScale = v => Math.sqrt(v / maxTokens);

This maps token values to [0, 1] using the square root, compressing large outliers while expanding the lower range. The same technique is used in Vega-Lite's "scale": {"type": "sqrt"}.

Canvas Circle Drawing

ctx.globalAlpha = 0.75;
ctx.fillStyle = modelColorMap[r.model];
ctx.beginPath();
ctx.arc(x, y, radius, 0, Math.PI * 2);
ctx.fill();

Each dot's radius is proportional to token count: 3 + (tokens / maxTokens) * 14.

Chart 2 — Stacked Histogram

Duration: 2

Requests are bucketed into token ranges (0–100, 100–500, 500–1K, 1K–5K, 5K–10K, 10K–20K, 20K+). Within each bucket, bars are stacked by model color.

Binning Strategy

const bins = [
  {label: "0-100", min: 0, max: 100},
  {label: "100-500", min: 100, max: 500},
  ...
];

Non-uniform bins capture the bimodal distribution common in Cortex API usage — many short completion calls alongside longer multi-turn conversations.

Chart 3 — Circle Plot (Bubble Matrix)

Duration: 2

Inspired by the Vega-Lite "Natural Disasters" example, this chart places one circle per date × model cell. Circle area encodes total tokens for that combination.

Circle Plot and Trellis

Sizing Formula

const radius = 6 + Math.sqrt(r.total_tokens / maxTokens) * 30;

The Math.sqrt ensures circle area scales linearly with tokens (since area ∝ r²).

Chart 4 — Trellis Dot Plot

Duration: 2

Faceted by model (one row per model), this strip plot shows individual request token values on a shared √ x-axis. It reveals per-model distributions at a glance — e.g., claude-sonnet-4-5 having a bimodal pattern of small and large requests.

Faceting Implementation

allModels.forEach((m, mi) => {
  const fy = margin.top + mi * facetH;
  // Draw model label, grid lines, then dots
  const modelReqs = requests.filter(r => r.model === m);
  ...
});

Chart 5 — Interactive Multi-Line Cumulative

Duration: 3

The full-width bottom chart shows cumulative tokens over time for each model. Hovering reveals a cross-model tooltip showing all models' totals at the nearest date.

Multi-Line Cumulative

Cumulative Calculation

allModels.forEach(model => {
  let cumul = 0;
  sorted.forEach(d => { cumul += d.tokens; byDate[d.date] = cumul; });
  // Fill forward for dates with no activity
  let last = 0;
  allDates.forEach(date => {
    if (byDate[date] !== undefined) last = byDate[date];
    filledData[model].push({date, cumulative: last});
  });
});

Mouse Hover Nearest-Date

canvas.addEventListener("mousemove", e => {
  const closestIdx = allDates.reduce((best, _, i) => {
    const x = margin.left + (i / (allDates.length - 1)) * plotW;
    return Math.abs(mx - x) < Math.abs(mx - bestX) ? i : best;
  }, 0);
  // Build tooltip with all models at this date
});

Customization Guide

Duration: 2

Using Your Own Data

Replace the requests array at the top of the <script> block with your SQL output. The dashboard auto-detects:

  • Models: derived from modelColorMap keys
  • Dates: extracted from the data array
  • Token ranges: fixed bins work for most usage patterns

Adding Models

Add entries to modelColorMap:

const modelColorMap = {
  "claude-sonnet-4-5": "#7c3aed",
  "claude-sonnet-4-6": "#a855f7",
  "claude-opus-4-6": "#f59e0b",
  "openai-gpt-5.2": "#10b981",
  "your-new-model": "#ec4899"  // add more here
};

Changing the Theme

Update three CSS values:

  • body { background: #0f1724; } — page background
  • .card { background: #1a2332; } — chart card background
  • h1, .card h2 { color: #29b5e8; } — accent color

Conclusion

Duration: 1

What You Learned

  • Querying per-request token data from CORTEX_REST_API_USAGE_HISTORY
  • Building five chart types with the HTML Canvas API and zero dependencies
  • Implementing interactive tooltips, retina scaling, and √ scales
  • Customizing the dashboard with your own data and color themes

Related Resources

Updated 2026-04-13

This content is provided as is, and is not maintained on an ongoing basis. It may be out of date with current Snowflake instances