Skip to content
Skillpedia
APIs & servers (backend)40k · #5410

upstash-redis

Helps your agent use Redis as a fast, in-memory database. It's useful for storing temporary data like user sessions or counters, and for limiting how many requests a user can make.

What it does

This tool lets you use the Redis database over the internet without complex connections. It's useful for storing temporary information (caching), managing user sessions, and limiting how often something can be done in a period (rate limiting).

When to use it

  • ✓When you need to store data temporarily for quick access.
  • ✓To manage logins and information for each connected user.
  • ✓To prevent a user from abusing a feature by limiting the number of requests.

Example of what to ask your AI

“Set the request limit to 10 per minute for the login page.”

Want more? Open the sections below.

How to use

The easiest way: copy the message below and paste it into Claude, ChatGPT, Cursor or any AI. It reads the skill and follows the instructions.

Skill link

https://github.com/github/awesome-copilot/blob/main/skills/upstash-redis/SKILL.md

Ready-to-paste message

Use this skill to help me: https://github.com/github/awesome-copilot/blob/main/skills/upstash-redis/SKILL.md Read the SKILL.md file at that link and follow its instructions for my task.
How it works

The tool works by sending commands to Redis via web requests (HTTP). It's configured with credentials you get from the Upstash Redis service.

Installation

Easiest way: copy the skill link and paste it into Claude, ChatGPT or Cursor asking it to follow the instructions.

In the terminal (Claude Code, Codex, Cursor), in your project folder:

npx skills add github/awesome-copilot --skill upstash-redis

Or download just the file:

curl -L https://raw.githubusercontent.com/github/awesome-copilot/main/skills/upstash-redis/SKILL.md -o SKILL.md
Technical content (original SKILL.md)

Original text by the author, straight from GitHub.

Upstash Redis Skill

This skill covers the three things serverless apps most often need Redis for: caching, sessions, and rate limiting. The client talks to Redis over HTTP, so it works where a long-lived TCP connection does not (edge middleware, short lived functions). Follow the steps in order; each ends with a checkpoint.

Requirements and limitations

  • An Upstash Redis database (hosted service; usage-based pricing with a free tier). Credentials are a REST URL and token from the database page.
  • Environment variables UPSTASH_REDIS_REST_URL and UPSTASH_REDIS_REST_TOKEN.
  • Every command is an HTTP request. Batch with pipeline() or MGET/MSET when you issue many commands per request; avoid KEYS * in production.
  • Values are serialized automatically (objects, arrays, numbers round-trip). Do not JSON.stringify before set or parseInt after get.

Step 1 — Install and create one client per module

npm install @upstash/redis @upstash/ratelimit
// lib/redis.ts
import { Redis } from "@upstash/redis";

// Reads UPSTASH_REDIS_REST_URL and UPSTASH_REDIS_REST_TOKEN
export const redis = Redis.fromEnv();

Create the client at module scope, not inside the request handler, so ephemeral caches and pipelines can be reused across invocations.

Checkpoint: await redis.ping() returns "PONG".

Step 2 — Cache-aside with TTL

import { redis } from "@/lib/redis";

type User = { id: string; name: string; plan: "free" | "pro" };

export async function getUser(userId: string): Promise<User | null> {
  const key = `user:${userId}`;
  const cached = await redis.get<User>(key);
  if (cached) return cached;

  const user = await db.users.findById(userId); // your data source
  if (user) await redis.set(key, user, { ex: 3600 }); // 1 hour TTL
  return user;
}

export async function updateUser(userId: string, patch: Partial<User>) {
  const user = await db.users.update(userId, patch);
  await redis.set(`user:${userId}`, user, { ex: 3600 }); // write-through
  return user;
}

export async function deleteUser(userId: string) {
  await db.users.delete(userId);
  await redis.del(`user:${userId}`); // invalidate
}

Always set a TTL on cache entries; namespace keys (user:123, session:abc).

Checkpoint: second call to getUser returns without hitting the database and await redis.ttl("user:123") is positive.

Step 3 — Sessions with sliding expiration

import { redis } from "@/lib/redis";

const SESSION_TTL = 60 * 60 * 24; // 24 hours

export async function createSession(userId: string, data: Record<string, unknown>) {
  const sessionId = crypto.randomUUID();
  await redis.set(`session:${sessionId}`, { userId, ...data, createdAt: Date.now() }, { ex: SESSION_TTL });
  return sessionId;
}

export async function getSession<T = Record<string, unknown>>(sessionId: string) {
  const session = await redis.get<T>(`session:${sessionId}`);
  if (session) await redis.expire(`session:${sessionId}`, SESSION_TTL); // slide
  return session;
}

export async function destroySession(sessionId: string) {
  await redis.del(`session:${sessionId}`);
}

Store the session id in an HttpOnly; Secure; SameSite cookie; never put the Redis token in client code.

Checkpoint: getSession after createSession returns the object with userId; after destroySession it returns null.

Step 4 — Rate limiting a route handler

// app/api/search/route.ts (Next.js App Router; same pattern for any fetch handler)
import { Ratelimit } from "@upstash/ratelimit";
import { Redis } from "@upstash/redis";

const ratelimit = new Ratelimit({
  redis: Redis.fromEnv(),
  limiter: Ratelimit.slidingWindow(10, "10 s"), // 10 requests per 10 seconds
  prefix: "ratelimit:search", // isolate keys per limiter
});

export async function POST(request: Request) {
  const ip = request.headers.get("x-forwarded-for")?.split(",")[0]?.trim() ?? "anonymous";
  const { success, limit, remaining, reset } = await ratelimit.limit(ip);

  if (!success) {
    return new Response("Too Many Requests", {
      status: 429,
      headers: {
        "X-RateLimit-Limit": String(limit),
        "X-RateLimit-Remaining": String(remaining),
        "Retry-After": String(Math.max(0, Math.ceil((reset - Date.now()) / 1000))),
      },
    });
  }

  // handle the request
  return Response.json({ ok: true });
}
  • Identifier: use the user id or API key when authenticated; fall back to IP.

…

FAQ

Do I need to install anything?

Yes, you need to install the `@upstash/redis` and `@upstash/ratelimit` libraries using a package manager like npm.

What are environment variables?

These are variables where you store sensitive information like passwords or access keys, such as the Upstash Redis URL and token, so they aren't exposed in the code.

Can I use this anywhere?

It works well in serverless and edge environments (like Vercel, Cloudflare Workers) where persistent network connections can be an issue. It's not ideal if you already have an established TCP Redis connection on a traditional server.

Details

Original description by the author

Use Redis over HTTP from serverless and edge runtimes with @upstash/redis, and add rate limiting with @upstash/ratelimit. Use when the user mentions Upstash Redis, needs Redis from a Next.js route handler or middleware, Vercel, Cloudflare Workers, Deno, or Bun without TCP connection pooling, or wants cache-aside with TTLs, a session store, counters, or a 429 rate limiter using fixed window, slidin

repo: github/awesome-copilot

Popularity

GitHub stars
40k
Ranking position
#5410
License
MIT
Updated
10/15/2026

Is this skill useful?

0

Sign in to vote.

Comments

  • …

More skills from this repository

Similar skills