use axum::Json;
use axum::body::Bytes;
use axum::extract::{Path, Query, State};
use axum::http::{HeaderMap, StatusCode};
use serde::{Deserialize, Serialize};
use super::auth::{AppState, auth_user, constant_time_eq, generate_token, sha256_hex};
use super::helpers::internal_error;
const MAX_PUBLISH_PER_HOUR: i64 = 20;
const MAX_BODY_BYTES: usize = 8 * 1024;
const MAX_TOP_COMMANDS: usize = 12;
const MAX_NAME_LEN: usize = 40;
const MAX_LABEL_LEN: usize = 60;
type ApiResult<T> = Result<T, (StatusCode, String)>;
fn err(status: StatusCode, code: &str) -> (StatusCode, String) {
(status, format!(r#"{{"error":"{code}"}}"#))
}
fn bad_payload() -> (StatusCode, String) {
err(StatusCode::BAD_REQUEST, "invalid_payload")
}
#[derive(Deserialize, Serialize)]
#[serde(deny_unknown_fields)]
pub(super) struct TopCommand {
pub name: String,
pub pct: f64,
}
#[derive(Deserialize, Serialize)]
#[serde(deny_unknown_fields)]
pub(super) struct PublishPayload {
pub period: String,
pub tokens_saved: i64,
pub cost_avoided_usd: f64,
pub pricing_estimated: bool,
pub compression_rate_pct: f64,
#[serde(default)]
pub total_commands: i64,
#[serde(default)]
pub sessions_count: i64,
#[serde(default)]
pub files_touched: i64,
#[serde(default)]
pub top_commands: Vec<TopCommand>,
#[serde(default)]
pub model_key: Option<String>,
#[serde(default)]
pub display_name: Option<String>,
#[serde(default)]
pub leaderboard_opt_in: bool,
}
impl PublishPayload {
fn validate(&self) -> ApiResult<()> {
if !matches!(self.period.as_str(), "day" | "week" | "month" | "all") {
return Err(bad_payload());
}
if self.tokens_saved < 0 || self.total_commands < 0 {
return Err(bad_payload());
}
if self.sessions_count < 0 || self.files_touched < 0 {
return Err(bad_payload());
}
if !finite_nonneg(self.cost_avoided_usd) {
return Err(bad_payload());
}
if !in_pct(self.compression_rate_pct) {
return Err(bad_payload());
}
if self.top_commands.len() > MAX_TOP_COMMANDS {
return Err(bad_payload());
}
for c in &self.top_commands {
let len = c.name.chars().count();
if len == 0 || len > MAX_NAME_LEN || has_markup(&c.name) || !in_pct(c.pct) {
return Err(bad_payload());
}
}
if let Some(m) = &self.model_key
&& (m.chars().count() > MAX_LABEL_LEN || has_markup(m))
{
return Err(bad_payload());
}
if let Some(name) = &self.display_name {
let len = name.chars().count();
if len == 0 || len > MAX_LABEL_LEN || has_markup(name) {
return Err(bad_payload());
}
}
Ok(())
}
fn to_report(&self) -> crate::core::wrapped::WrappedReport {
crate::core::wrapped::WrappedReport {
period: self.period.clone(),
tokens_saved: u64::try_from(self.tokens_saved).unwrap_or(0),
tokens_input: 0,
cost_avoided_usd: self.cost_avoided_usd,
total_commands: u64::try_from(self.total_commands).unwrap_or(0),
sessions_count: usize::try_from(self.sessions_count).unwrap_or(0),
top_commands: self
.top_commands
.iter()
.map(|c| (c.name.clone(), 0u64, c.pct))
.collect(),
compression_rate_pct: self.compression_rate_pct,
files_touched: u64::try_from(self.files_touched).unwrap_or(0),
daily_savings: Vec::new(),
bounce_tokens: 0,
model_key: self.model_key.clone().unwrap_or_default(),
pricing_estimated: self.pricing_estimated,
percentile: None,
}
}
}
fn finite_nonneg(v: f64) -> bool {
v.is_finite() && v >= 0.0
}
fn in_pct(v: f64) -> bool {
v.is_finite() && (0.0..=100.0).contains(&v)
}
fn has_markup(s: &str) -> bool {
s.chars()
.any(|c| c == '<' || c == '>' || (c.is_control() && c != '\t'))
}
const PUBLISHER_ID_HEX_LEN: usize = 32;
#[derive(Deserialize)]
struct SignedEnvelope {
payload_json: String,
public_key: Option<String>,
signature: Option<String>,
}
fn verify_signed_envelope(env: &SignedEnvelope) -> ApiResult<(PublishPayload, String)> {
use crate::core::agent_identity::{hex_decode, verify_signature};
let (Some(pk_hex), Some(sig_hex)) = (&env.public_key, &env.signature) else {
return Err(bad_payload());
};
let pk_bytes = hex_decode(pk_hex).map_err(|_| bad_payload())?;
let sig_bytes = hex_decode(sig_hex).map_err(|_| bad_payload())?;
if !verify_signature(&pk_bytes, env.payload_json.as_bytes(), &sig_bytes) {
return Err(err(StatusCode::UNAUTHORIZED, "invalid_signature"));
}
let payload: PublishPayload =
serde_json::from_str(&env.payload_json).map_err(|_| bad_payload())?;
let publisher_id = sha256_hex(pk_hex)
.get(..PUBLISHER_ID_HEX_LEN)
.ok_or_else(internal_error_str)?
.to_string();
Ok((payload, publisher_id))
}
fn internal_error_str() -> (StatusCode, String) {
err(StatusCode::INTERNAL_SERVER_ERROR, "internal_error")
}
pub(super) async fn publish(
State(state): State<AppState>,
headers: HeaderMap,
body: Bytes,
) -> ApiResult<(StatusCode, Json<serde_json::Value>)> {
if body.len() > MAX_BODY_BYTES {
return Err(err(StatusCode::PAYLOAD_TOO_LARGE, "payload_too_large"));
}
let (payload, payload_json, publisher_id) = if let Ok(env) =
serde_json::from_slice::<SignedEnvelope>(&body)
{
let (payload, pid) = verify_signed_envelope(&env)?;
(payload, env.payload_json, Some(pid))
} else {
let payload: PublishPayload = serde_json::from_slice(&body).map_err(|_| bad_payload())?;
let json = serde_json::to_string(&payload).map_err(internal_error)?;
(payload, json, None)
};
payload.validate()?;
let client = state.pool.get().await.map_err(internal_error)?;
let ip_hash = client_ip_hash(&headers, &state.cfg.ip_hash_salt);
if let Some(h) = &ip_hash {
let row = client
.query_one(
"SELECT count(*) FROM wrapped_cards \
WHERE ip_hash = $1 AND created_at > now() - interval '1 hour'",
&[h],
)
.await
.map_err(internal_error)?;
let recent: i64 = row.get(0);
if recent >= MAX_PUBLISH_PER_HOUR {
return Err(err(StatusCode::TOO_MANY_REQUESTS, "rate_limited"));
}
}
let id = generate_card_id();
let edit_token = generate_token();
let edit_token_hash = sha256_hex(&edit_token);
let base = state.cfg.public_base_url.trim_end_matches('/');
if let Some(pid) = &publisher_id {
let row = client
.query_one(
"INSERT INTO wrapped_cards \
(id, edit_token_hash, payload_json, ip_hash, leaderboard_opt_in, tokens_saved, publisher_id, period) \
VALUES ($1, $2, $3, $4, $5, $6, $7, $8) \
ON CONFLICT (publisher_id, period) WHERE publisher_id IS NOT NULL \
DO UPDATE SET payload_json = EXCLUDED.payload_json, \
leaderboard_opt_in = EXCLUDED.leaderboard_opt_in, \
tokens_saved = EXCLUDED.tokens_saved \
RETURNING id, (xmax = 0) AS inserted",
&[
&id,
&edit_token_hash,
&payload_json,
&ip_hash,
&payload.leaderboard_opt_in,
&payload.tokens_saved,
pid,
&payload.period,
],
)
.await
.map_err(internal_error)?;
let final_id: String = row.get(0);
let inserted: bool = row.get(1);
let url = format!("{base}/w/{final_id}");
let mut out = serde_json::json!({ "id": final_id, "url": url });
if inserted {
out["edit_token"] = serde_json::Value::String(edit_token);
Ok((StatusCode::CREATED, Json(out)))
} else {
Ok((StatusCode::OK, Json(out)))
}
} else {
client
.execute(
"INSERT INTO wrapped_cards \
(id, edit_token_hash, payload_json, ip_hash, leaderboard_opt_in, tokens_saved, period) \
VALUES ($1, $2, $3, $4, $5, $6, $7)",
&[
&id,
&edit_token_hash,
&payload_json,
&ip_hash,
&payload.leaderboard_opt_in,
&payload.tokens_saved,
&payload.period,
],
)
.await
.map_err(internal_error)?;
let url = format!("{base}/w/{id}");
Ok((
StatusCode::CREATED,
Json(serde_json::json!({ "id": id, "edit_token": edit_token, "url": url })),
))
}
}
pub(super) async fn get_card(
State(state): State<AppState>,
Path(id): Path<String>,
) -> ApiResult<Json<serde_json::Value>> {
let client = state.pool.get().await.map_err(internal_error)?;
let row = client
.query_opt(
"UPDATE wrapped_cards SET view_count = view_count + 1 \
WHERE id = $1 RETURNING payload_json, created_at, view_count",
&[&id],
)
.await
.map_err(internal_error)?;
let Some(row) = row else {
return Err(err(StatusCode::NOT_FOUND, "not_found"));
};
let payload_json: String = row.get(0);
let created_at: chrono::DateTime<chrono::Utc> = row.get(1);
let view_count: i64 = row.get(2);
let card: serde_json::Value = serde_json::from_str(&payload_json).map_err(internal_error)?;
Ok(Json(serde_json::json!({
"id": id,
"created_at": created_at.to_rfc3339(),
"view_count": view_count,
"card": card,
})))
}
pub(super) async fn get_card_svg(
State(state): State<AppState>,
Path(id): Path<String>,
) -> ApiResult<axum::response::Response> {
let svg = fetch_card_svg(&state, &id).await?;
use axum::http::header::{CACHE_CONTROL, CONTENT_TYPE};
use axum::response::IntoResponse;
Ok((
[
(CONTENT_TYPE, "image/svg+xml; charset=utf-8"),
(CACHE_CONTROL, "public, max-age=86400"),
],
svg,
)
.into_response())
}
pub(super) async fn get_card_png(
State(state): State<AppState>,
Path(id): Path<String>,
) -> ApiResult<axum::response::Response> {
let svg = fetch_card_svg(&state, &id).await?;
let png = svg_to_png(&svg).map_err(internal_error)?;
use axum::http::header::{CACHE_CONTROL, CONTENT_TYPE};
use axum::response::IntoResponse;
Ok((
[
(CONTENT_TYPE, "image/png"),
(CACHE_CONTROL, "public, max-age=86400"),
],
png,
)
.into_response())
}
pub(super) async fn get_permalink_page(
State(state): State<AppState>,
Path(id): Path<String>,
) -> ApiResult<axum::response::Response> {
let client = state.pool.get().await.map_err(internal_error)?;
let row = client
.query_opt(
"UPDATE wrapped_cards SET view_count = view_count + 1 \
WHERE id = $1 RETURNING payload_json",
&[&id],
)
.await
.map_err(internal_error)?;
let Some(row) = row else {
return Err(err(StatusCode::NOT_FOUND, "not_found"));
};
let payload_json: String = row.get(0);
let payload: PublishPayload = serde_json::from_str(&payload_json).map_err(internal_error)?;
let html = render_permalink_html(
&id,
&payload,
&state.cfg.public_base_url,
&state.cfg.api_base_url,
);
use axum::http::header::CONTENT_TYPE;
use axum::response::IntoResponse;
Ok(([(CONTENT_TYPE, "text/html; charset=utf-8")], html).into_response())
}
#[derive(Serialize)]
pub(super) struct LeaderRow {
rank: usize,
id: String,
url: String,
display_name: Option<String>,
tokens_saved: i64,
cost_avoided_usd: f64,
compression_rate_pct: f64,
period: String,
pricing_estimated: bool,
flagged: bool,
}
#[derive(Serialize)]
pub(super) struct Leaderboard {
entries: Vec<LeaderRow>,
page: i64,
per_page: i64,
total_entries: i64,
total_pages: i64,
total_tokens_saved: i64,
total_cost_avoided_usd: f64,
}
#[derive(Debug, Default, Deserialize)]
pub(super) struct LeaderboardQuery {
page: Option<i64>,
per_page: Option<i64>,
q: Option<String>,
}
const LEADERBOARD_PER_PAGE_DEFAULT: i64 = 50;
const LEADERBOARD_PER_PAGE_MAX: i64 = 100;
const LEADERBOARD_MAX_CARDS: i64 = 50_000;
const IMPLAUSIBLE_RATE_PCT: f64 = 97.0;
const IMPLAUSIBLE_MIN_TOKENS: i64 = 1_000_000_000;
fn stats_implausible(tokens_saved: i64, compression_rate_pct: f64) -> bool {
tokens_saved >= IMPLAUSIBLE_MIN_TOKENS && compression_rate_pct >= IMPLAUSIBLE_RATE_PCT
}
fn rank_and_demote_flagged(entries: &mut [LeaderRow]) {
entries.sort_by_key(|e| e.flagged);
for (i, e) in entries.iter_mut().enumerate() {
e.rank = i + 1;
}
}
pub(super) async fn leaderboard(
State(state): State<AppState>,
Query(query): Query<LeaderboardQuery>,
) -> ApiResult<Json<Leaderboard>> {
Ok(Json(build_leaderboard(&state, &query).await?))
}
pub(super) async fn get_leaderboard_page(
State(state): State<AppState>,
Query(query): Query<LeaderboardQuery>,
) -> ApiResult<axum::response::Response> {
let board = build_leaderboard(&state, &query).await?;
let html = render_leaderboard_html(&board, query.q.as_deref(), &state.cfg.public_base_url);
use axum::http::header::CONTENT_TYPE;
use axum::response::IntoResponse;
Ok(([(CONTENT_TYPE, "text/html; charset=utf-8")], html).into_response())
}
async fn build_leaderboard(state: &AppState, query: &LeaderboardQuery) -> ApiResult<Leaderboard> {
let all = all_ranked_cards(state).await?;
Ok(paginate(all, query))
}
fn paginate(all: Vec<LeaderRow>, query: &LeaderboardQuery) -> Leaderboard {
let total_tokens_saved = all
.iter()
.map(|e| e.tokens_saved)
.fold(0i64, i64::saturating_add);
let total_cost_avoided_usd = all.iter().map(|e| e.cost_avoided_usd).sum();
let filtered: Vec<LeaderRow> = match query.q.as_deref().map(str::trim) {
Some(needle) if !needle.is_empty() => {
let needle = needle.to_lowercase();
all.into_iter()
.filter(|e| {
e.display_name
.as_deref()
.is_some_and(|n| n.to_lowercase().contains(&needle))
})
.collect()
}
_ => all,
};
let per_page = query
.per_page
.unwrap_or(LEADERBOARD_PER_PAGE_DEFAULT)
.clamp(1, LEADERBOARD_PER_PAGE_MAX);
let total_entries = filtered.len() as i64;
let total_pages = ((total_entries + per_page - 1) / per_page).max(1);
let page = query.page.unwrap_or(1).clamp(1, total_pages);
let start = ((page - 1) * per_page) as usize;
let entries: Vec<LeaderRow> = filtered
.into_iter()
.skip(start)
.take(per_page as usize)
.collect();
Leaderboard {
entries,
page,
per_page,
total_entries,
total_pages,
total_tokens_saved,
total_cost_avoided_usd,
}
}
async fn all_ranked_cards(state: &AppState) -> ApiResult<Vec<LeaderRow>> {
let client = state.pool.get().await.map_err(internal_error)?;
let rows = client
.query(
"SELECT id, payload_json, user_id::text, COALESCE(publisher_id, id) FROM ( \
SELECT DISTINCT ON (COALESCE(publisher_id, id)) \
id, payload_json, tokens_saved, created_at, user_id, publisher_id \
FROM wrapped_cards \
WHERE leaderboard_opt_in = TRUE \
ORDER BY COALESCE(publisher_id, id), tokens_saved DESC, created_at DESC \
) t \
ORDER BY tokens_saved DESC, created_at DESC LIMIT $1",
&[&LEADERBOARD_MAX_CARDS],
)
.await
.map_err(internal_error)?;
let raw: Vec<RawLeaderCard> = rows
.iter()
.map(|r| RawLeaderCard {
id: r.get(0),
payload_json: r.get(1),
user_id: r.get(2),
pub_key: r.get(3),
})
.collect();
let base = state.cfg.public_base_url.trim_end_matches('/');
let mut entries = aggregate_by_account(raw, base);
rank_and_demote_flagged(&mut entries);
Ok(entries)
}
struct RawLeaderCard {
id: String,
payload_json: String,
user_id: Option<String>,
pub_key: String,
}
fn aggregate_by_account(raw: Vec<RawLeaderCard>, base: &str) -> Vec<LeaderRow> {
use std::collections::HashMap;
struct Acc {
rep_tokens: i64,
rep_id: String,
rep_display_name: Option<String>,
rep_period: String,
rep_rate: f64,
sum_tokens: i64,
sum_cost: f64,
rate_num: f64,
rate_den: i64,
pricing_estimated: bool,
}
let mut groups: HashMap<String, Acc> = HashMap::new();
for c in raw {
let Ok(p) = serde_json::from_str::<PublishPayload>(&c.payload_json) else {
continue;
};
let key = match c.user_id.as_deref() {
Some(u) if !u.is_empty() => format!("u:{u}"),
_ => format!("p:{}", c.pub_key),
};
let acc = groups.entry(key).or_insert_with(|| Acc {
rep_tokens: i64::MIN,
rep_id: String::new(),
rep_display_name: None,
rep_period: String::new(),
rep_rate: 0.0,
sum_tokens: 0,
sum_cost: 0.0,
rate_num: 0.0,
rate_den: 0,
pricing_estimated: false,
});
let tokens = p.tokens_saved;
acc.sum_tokens = acc.sum_tokens.saturating_add(tokens);
acc.sum_cost += p.cost_avoided_usd;
if tokens > 0 {
acc.rate_num += p.compression_rate_pct * tokens as f64;
acc.rate_den = acc.rate_den.saturating_add(tokens);
}
acc.pricing_estimated |= p.pricing_estimated;
if tokens > acc.rep_tokens {
acc.rep_tokens = tokens;
acc.rep_id = c.id;
acc.rep_display_name = p.display_name;
acc.rep_period = p.period;
acc.rep_rate = p.compression_rate_pct;
}
}
let mut rows: Vec<LeaderRow> = groups
.into_values()
.map(|a| {
let rate = if a.rate_den > 0 {
a.rate_num / a.rate_den as f64
} else {
a.rep_rate
};
LeaderRow {
rank: 0, url: format!("{base}/w/{}", a.rep_id),
id: a.rep_id,
display_name: a.rep_display_name,
tokens_saved: a.sum_tokens,
cost_avoided_usd: a.sum_cost,
compression_rate_pct: rate,
period: a.rep_period,
pricing_estimated: a.pricing_estimated,
flagged: stats_implausible(a.sum_tokens, rate),
}
})
.collect();
rows.sort_by(|x, y| {
y.tokens_saved
.cmp(&x.tokens_saved)
.then_with(|| x.id.cmp(&y.id))
});
rows
}
fn render_leaderboard_html(board: &Leaderboard, q: Option<&str>, public_base: &str) -> String {
let base = public_base.trim_end_matches('/');
let needle = q.map(str::trim).filter(|s| !s.is_empty());
let mut items = String::new();
for row in &board.entries {
let name = row
.display_name
.as_deref()
.map_or_else(|| "anonymous".to_string(), html_escape);
let tokens_u = u64::try_from(row.tokens_saved).unwrap_or(0);
let tokens = crate::core::wrapped::format_tokens(tokens_u);
let energy = crate::core::energy::format_for_tokens(tokens_u);
let comp = format!("{:.0}%", row.compression_rate_pct);
let est = if row.pricing_estimated { " est." } else { "" };
let rank_class = if row.flagged {
" lc-flagged"
} else {
match row.rank {
1 => " lc-rank-1",
2 => " lc-rank-2",
3 => " lc-rank-3",
_ => "",
}
};
let flag_badge = if row.flagged {
r#"<span class="lc-flag" title="Self-reported figures that look statistically implausible (very high compression over very large volume). Not server-verified.">unverified</span>"#
} else {
""
};
items.push_str(&format!(
r#"<li><a class="lc-row{rank_class}" href="{url}"><span class="lc-rank">#{rank}</span><span class="lc-id"><span class="lc-name">{name}</span><span class="lc-period">{period}</span>{flag_badge}</span><span class="lc-stats"><span class="lc-num">{tokens}</span><span class="lc-meta">{comp} compressed · {energy} saved</span><span class="lc-usd">${cost:.0}{est}</span></span></a></li>"#,
url = row.url,
rank = row.rank,
cost = row.cost_avoided_usd,
period = html_escape(&row.period),
));
}
let board_html = if board.entries.is_empty() {
match needle {
Some(term) => format!(
r#"<div class="lc-empty">No one on the board matches <strong>{term}</strong>.<br/><a href="{base}/leaderboard">Clear search</a></div>"#,
term = html_escape(term)
),
None => r#"<div class="lc-empty">No one has opted in yet — be the first:<br/><code>lean-ctx gain --publish --leaderboard</code></div>"#.to_string(),
}
} else {
format!(r#"<ol class="lc-board">{items}</ol>"#)
};
let q_attr = needle.map(html_escape).unwrap_or_default();
let clear = if needle.is_some() {
format!(r#"<a class="lc-search-clear" href="{base}/leaderboard">Clear</a>"#)
} else {
String::new()
};
let search = format!(
r#"<form class="lc-search" method="get" action="{base}/leaderboard" role="search">
<input class="lc-search-input" type="search" name="q" value="{q_attr}" placeholder="Search by name…" aria-label="Search the leaderboard by name" autocomplete="off"/>
<button class="lc-search-btn" type="submit">Search</button>
{clear}
</form>"#
);
let count_line = if board.total_entries > 0 {
let n = board.total_entries;
let label = if n == 1 { "entry" } else { "entries" };
match needle {
Some(term) => format!(
r#"<p class="lc-count">{n} {label} matching <strong>{term}</strong></p>"#,
term = html_escape(term)
),
None => format!(r#"<p class="lc-count">{n} {label} on the board</p>"#),
}
} else {
String::new()
};
let q_param = needle
.map(|t| format!("&q={}", urlencoding::encode(t)))
.unwrap_or_default();
let pp_param = if board.per_page == LEADERBOARD_PER_PAGE_DEFAULT {
String::new()
} else {
format!("&per_page={}", board.per_page)
};
let page_url = |n: i64| format!("{base}/leaderboard?page={n}{pp_param}{q_param}");
let pagination = if board.total_pages > 1 {
let prev = if board.page > 1 {
format!(
r#"<a class="lc-page-btn" href="{}" rel="prev">← Prev</a>"#,
page_url(board.page - 1)
)
} else {
r#"<span class="lc-page-btn lc-page-btn-off" aria-disabled="true">← Prev</span>"#
.to_string()
};
let next = if board.page < board.total_pages {
format!(
r#"<a class="lc-page-btn" href="{}" rel="next">Next →</a>"#,
page_url(board.page + 1)
)
} else {
r#"<span class="lc-page-btn lc-page-btn-off" aria-disabled="true">Next →</span>"#
.to_string()
};
format!(
r#"<nav class="lc-pagination" aria-label="Leaderboard pages">{prev}<span class="lc-page-info">Page {page} / {total}</span>{next}</nav>"#,
page = board.page,
total = board.total_pages,
)
} else {
String::new()
};
let head = format!(
r#"<meta charset="utf-8"/>
<meta name="viewport" content="width=device-width, initial-scale=1"/>
<title>lean-ctx Leaderboard — top realized token savings</title>
<meta name="description" content="Top token savings, opted in by lean-ctx users. Open source — your AI sees only what matters."/>
<link rel="canonical" href="{base}/leaderboard"/>
{fonts}
<style>{css}</style>"#,
fonts = super::site_theme::FONT_LINKS,
css = super::site_theme::THEME_CSS,
);
format!(
r#"<!doctype html>
<html lang="en">
<head>
{head}
</head>
<body>
{header}
<main class="lc-container">
<section class="lc-hero">
<span class="lc-label">Self-reported savings</span>
<h1>Leaderboard</h1>
<p>The most realized token savings, opted in by lean-ctx users. Figures are self-reported from each user's local ledger — not server-verified. Cards whose stats look statistically implausible are flagged <span class="lc-flag">unverified</span> and ranked last.</p>
</section>
{search}
{count_line}
{board_html}
{pagination}
<section class="lc-cta-section">
<h2>Put your savings on the board</h2>
<p>Install lean-ctx, then publish your Wrapped recap.</p>
<a class="lc-cta" href="{base}/docs/getting-started/">Install lean-ctx</a>
</section>
</main>
{footer}
</body>
</html>"#,
header = super::site_theme::header(base),
footer = super::site_theme::footer(base),
)
}
async fn fetch_card_svg(state: &AppState, id: &str) -> ApiResult<String> {
let client = state.pool.get().await.map_err(internal_error)?;
let row = client
.query_opt(
"SELECT payload_json FROM wrapped_cards WHERE id = $1",
&[&id],
)
.await
.map_err(internal_error)?;
let Some(row) = row else {
return Err(err(StatusCode::NOT_FOUND, "not_found"));
};
let payload_json: String = row.get(0);
let payload: PublishPayload = serde_json::from_str(&payload_json).map_err(internal_error)?;
Ok(payload.to_report().to_svg())
}
fn svg_to_png(svg: &str) -> Result<Vec<u8>, String> {
use resvg::{tiny_skia, usvg};
let mut opt = usvg::Options::default();
{
let db = opt.fontdb_mut();
db.load_system_fonts();
db.set_serif_family("DejaVu Serif");
db.set_sans_serif_family("DejaVu Sans");
db.set_monospace_family("DejaVu Sans Mono");
}
opt.font_family = "DejaVu Sans".to_string();
let tree = usvg::Tree::from_str(svg, &opt).map_err(|e| format!("svg parse: {e}"))?;
let size = tree.size().to_int_size();
let mut pixmap = tiny_skia::Pixmap::new(size.width(), size.height())
.ok_or_else(|| "pixmap alloc failed".to_string())?;
resvg::render(&tree, tiny_skia::Transform::default(), &mut pixmap.as_mut());
pixmap.encode_png().map_err(|e| format!("png encode: {e}"))
}
fn html_escape(s: &str) -> String {
s.replace('&', "&")
.replace('<', "<")
.replace('>', ">")
.replace('"', """)
.replace('\'', "'")
}
fn render_permalink_html(
id: &str,
p: &PublishPayload,
public_base: &str,
api_base: &str,
) -> String {
let report = p.to_report();
let svg = report.to_svg();
let tokens = crate::core::wrapped::format_tokens(report.tokens_saved);
let cost = format!("${:.2}", report.cost_avoided_usd);
let est = if report.pricing_estimated {
" (est.)"
} else {
""
};
let who = p.display_name.as_deref().map(html_escape);
let title = match &who {
Some(n) => format!("{n}'s lean-ctx Wrapped"),
None => "lean-ctx Wrapped".to_string(),
};
let description = format!(
"Saved {tokens} tokens (~{cost}{est}) with lean-ctx — my AI saw only what mattered."
);
let page_url = format!("{}/w/{}", public_base.trim_end_matches('/'), id);
let img_url = format!(
"{}/api/wrapped/{}/card.png",
api_base.trim_end_matches('/'),
id
);
let base = public_base.trim_end_matches('/');
format!(
r#"<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8"/>
<meta name="viewport" content="width=device-width, initial-scale=1"/>
<title>{title}</title>
<meta name="description" content="{description}"/>
<link rel="canonical" href="{page_url}"/>
<meta property="og:type" content="website"/>
<meta property="og:site_name" content="lean-ctx"/>
<meta property="og:title" content="{title}"/>
<meta property="og:description" content="{description}"/>
<meta property="og:url" content="{page_url}"/>
<meta property="og:image" content="{img_url}"/>
<meta property="og:image:width" content="1200"/>
<meta property="og:image:height" content="630"/>
<meta name="twitter:card" content="summary_large_image"/>
<meta name="twitter:title" content="{title}"/>
<meta name="twitter:description" content="{description}"/>
<meta name="twitter:image" content="{img_url}"/>
{fonts}
<style>{css}</style>
</head>
<body>
{header}
<main class="lc-container">
<section class="lc-card-wrap">
{svg}
</section>
<section class="lc-cta-section">
<h2>Make your own Wrapped</h2>
<p>Install lean-ctx — your AI sees only what matters.</p>
<a class="lc-cta" href="{base}/docs/getting-started/">Install lean-ctx</a>
</section>
</main>
{footer}
</body>
</html>"#,
fonts = super::site_theme::FONT_LINKS,
css = super::site_theme::THEME_CSS,
header = super::site_theme::header(base),
footer = super::site_theme::footer(base),
)
}
pub(super) async fn delete_card(
State(state): State<AppState>,
headers: HeaderMap,
Path(id): Path<String>,
) -> ApiResult<Json<serde_json::Value>> {
let token =
edit_token_header(&headers).ok_or_else(|| err(StatusCode::FORBIDDEN, "forbidden"))?;
let client = state.pool.get().await.map_err(internal_error)?;
let stored = fetch_token_hash(&client, &id).await?;
require_token(&token, &stored)?;
client
.execute("DELETE FROM wrapped_cards WHERE id = $1", &[&id])
.await
.map_err(internal_error)?;
Ok(Json(serde_json::json!({ "deleted": true })))
}
pub(super) async fn claim_card(
State(state): State<AppState>,
headers: HeaderMap,
Path(id): Path<String>,
) -> ApiResult<Json<serde_json::Value>> {
let (user_id, _) = auth_user(&state, &headers).await?;
let token =
edit_token_header(&headers).ok_or_else(|| err(StatusCode::FORBIDDEN, "forbidden"))?;
let client = state.pool.get().await.map_err(internal_error)?;
let stored = fetch_token_hash(&client, &id).await?;
require_token(&token, &stored)?;
client
.execute(
"UPDATE wrapped_cards SET user_id = $1 WHERE id = $2",
&[&user_id, &id],
)
.await
.map_err(internal_error)?;
Ok(Json(serde_json::json!({ "claimed": true })))
}
async fn fetch_token_hash(client: &tokio_postgres::Client, id: &str) -> ApiResult<String> {
let row = client
.query_opt(
"SELECT edit_token_hash FROM wrapped_cards WHERE id = $1",
&[&id],
)
.await
.map_err(internal_error)?;
match row {
Some(r) => Ok(r.get(0)),
None => Err(err(StatusCode::NOT_FOUND, "not_found")),
}
}
fn require_token(presented: &str, stored_hash: &str) -> ApiResult<()> {
if constant_time_eq(sha256_hex(presented).as_bytes(), stored_hash.as_bytes()) {
Ok(())
} else {
Err(err(StatusCode::FORBIDDEN, "forbidden"))
}
}
fn edit_token_header(headers: &HeaderMap) -> Option<String> {
let v = headers.get("x-edit-token")?.to_str().ok()?.trim();
(!v.is_empty()).then(|| v.to_string())
}
fn generate_card_id() -> String {
let bytes: [u8; 16] = rand::random();
hex::encode(bytes)
}
fn client_ip_hash(headers: &HeaderMap, salt: &str) -> Option<String> {
let ip = headers
.get("x-forwarded-for")
.and_then(|v| v.to_str().ok())
.and_then(|s| s.split(',').next())
.map(str::trim)
.filter(|s| !s.is_empty())
.or_else(|| {
headers
.get("x-real-ip")
.and_then(|v| v.to_str().ok())
.map(str::trim)
.filter(|s| !s.is_empty())
})?;
Some(sha256_hex(&format!("{salt}:{ip}")))
}
#[cfg(test)]
mod tests;