Upstash が PlanTripAI の急成長を促進:主要戦略と成功事例
この記事では、AI 主導の旅行計画スタートアップである PlanTripAI の開発における Upstash の極めて重要な役割について探ります。 Upstash Redis の利用は、ユーザー アクセスのためのキー ライセンスの保存や旅行コンテンツの効率的な保存とキャッシュなどの重要な側面を管理するために非常に重要です。さらに、Upstash のレート制限機能は、システムを保護する上で重要な役割を果たします。リクエストの頻度を効果的に管理し、潜在的なセキュリティ脅威に対する堅牢な保護を提供し、ユーザーにスムーズで中断のないサービスを保証します。
plantripai.com は、目的地、滞在期間、旅行スタイル、予算などのユーザーの好みに基づいてパーソナライズされた旅程を迅速に作成する AI ベースの旅行プランナーです。無制限の旅程作成とさまざまなダウンロード形式が提供されます。
- @upstash/redis
- @upstash/ratelimit
- next.js
仕組み
AI 企業は通常、ユーザーが製品を試すための複数の方法を提供します。 PlanTripAI では、フリーミアムと有料プランの両方を提供しています。
フリーミアムで最も人気のあるプランでは、ユーザーが有効なライセンスなしで旅行を作成するたびに、新しいランダム キーが生成され、Redis ハッシュ (redis.hset(trip:${key}, data)) に保存されます。 、旅行の内容とともに。このキーにより、旅行の詳細ページへの一時的なアクセスが許可されます。このアクセスの有効期限が切れると、ユーザーは旅行への永続的なアクセスを維持するかどうかを決定できます。
さらに、フリーミアム ユーザーにはレート制限 (fixedWindow) が適用されます。 ) は 10 秒あたり 3 リクエストに相当します。これは、アプリケーションに対する潜在的な攻撃を防ぐのに役立ちます。

有料プランについては、ユーザーはペイメントゲートウェイを通じて製品を購入できます。トランザクションが成功すると、支払いゲートウェイの Webhook が成功イベントを発行し、キーが有効なキー (redis.set(${licenseKey}, true)) として Redis に保存されます。 .
有効なライセンスを持つユーザーが旅行を作成すると、ランダムなキーが生成され、Redis に保存されます。さらに、新しい旅行はユーザー オブジェクトに保存され、ライセンス キーにリンクされます。
有料ユーザーは、フリーミアム ユーザーよりも寛大なレート制限を享受できます。この拡張機能は、Redis で有効なキーをチェックすることによって動的に提供されます。

旅行データの保存
PlanTripAI は Redis を利用してユーザーが作成した旅行を保存します。 Redis は、高速な Key-Value ストアとしての効率性の点で、私たちにとって理想的な選択肢です。旅行は一度作成されると不変であり、ハッシュを使用することでキー データと一緒にメタデータを保存できることを考えると。
旅行データは、Redis ハッシュで次のように構造化されます。
{
"itinerary": [
{ "day": "Day 1", "data": [...] }
],
"info": "This itinerary is designed for a city explorer visiting Paris, France for 2 days.",
"inputs": {
"city": "Paris, France",
"days": 2,
"accommodation": "Paris France Hotel",
"kind": "city explorer",
"currency": "USD",
"budget": 3000,
"transportation": "bus"
},
"createdAt": ...,
"shareable": false
} HTTP 経由で Upstash Redis API を使用すると、データは無料の Redis データベースに保存されます。このデータベースは、1 日あたり 10,000 件のリクエストを無料で提供しますが、これは私たちのニーズにとって十分以上です。
import { Redis } from "@upstash/redis";
const redis = new Redis({
url: "..." // UPSTASH_REDIS_REST_URL
token: "..." // UPSTASH_REDIS_REST_TOKEN
});
redis.hset(`trip:${id}`, data); 有効なライセンス キーの保存
前述したように、PlanTripAI のすべての機能にアクセスする 1 つの方法は、有料サブスクリプションを経由することです。この場合、各有料ユーザーには、Redis に保存されている有効なライセンス キーが割り当てられます。 Redis のキー/値データベースとしての効率性を考慮すると、この設定は迅速な検証チェックに最適です。
ユーザーを有効としてマークするには、次のコマンドを実行します。
import { Redis } from "@upstash/redis";
const redis = new Redis({
url: "..." // UPSTASH_REDIS_REST_URL
token: "..." // UPSTASH_REDIS_REST_TOKEN
});
await redis.set(licenseKey, true); ユーザーの正当性を確認するには、次のコマンドを使用します。
import { Redis } from "@upstash/redis";
const redis = new Redis({
url: "..." // UPSTASH_REDIS_REST_URL
token: "..." // UPSTASH_REDIS_REST_TOKEN
});
const redisLicenseKey = await redis.get(licenseKey);
const valid = Boolean(redisLicenseKey);
if (!valid) {
return new Response(
JSON.stringify({ message: "The license key is invalid!" }),
{
status: 401,
}
);
}
// successful code here...
レート制限の実装
アプリケーションを保護するための重要な機能は、Upstash Rate Limit によってサポートされるレート制限ロジックです。詳細については、こちらをご覧ください。このサービスは、無料ユーザーと有料ユーザーの両方にとってシームレスなエクスペリエンスを維持するために非常に重要であり、アプリケーション全体に影響を与えることなく悪意のあるユーザーからの攻撃を阻止することに成功しました。
以下は、ミドルウェアとして next.js を使用したコード スニペットです。このコードは、ユーザーの IP チェックを管理し、後続のリクエストを続行するかどうかを決定するのに役立ちます。
import {
NextResponse,
type NextFetchEvent,
type NextRequest,
} from "next/server";
import { Ratelimit } from "@upstash/ratelimit";
import { Redis } from "@upstash/redis";
const cache = new Map();
const ratelimit = new Ratelimit({
redis: Redis.fromEnv(),
limiter: Ratelimit.fixedWindow(3, "10s"),
ephemeralCache: cache,
analytics: true,
});
export default async function middleware(
request: NextRequest,
event: NextFetchEvent
): Promise<Response | undefined> {
const id = request.ip ?? "anonymous";
// optional hard coded IPs
const blockeds = [];
if (blockeds.includes(id.trim())) {
new NextResponse(
JSON.stringify({
message: "Blocked :)",
}),
{ status: 429, headers: { "Content-Type": "application/json" } }
);
}
const { success, pending, limit, reset, remaining } = await ratelimit.limit(
id
);
event.waitUntil(pending);
request.headers.set("X-RateLimit-Limit", limit.toString());
request.headers.set("X-RateLimit-Remaining", remaining.toString());
request.headers.set("X-RateLimit-Reset", reset.toString());
return success
? NextResponse.next()
: new NextResponse(
JSON.stringify({
message:
"Request cannot be processed! You sent too many requests in a given amount of time.",
}),
{ status: 429, headers: { "Content-Type": "application/json" } }
);
}
export const config = {
matcher: ["/api/generate-trip", "/api/get-license/(.*)"],
}; 最後の言葉
読んでいただきありがとうございます! PlanTripAI は、SaaS フレームワークで Upstash Redis と Next.js を統合するという私の好奇心から生まれたサイド プロジェクトとして始まりました。
この内容が有益で洞察力に富んだものであることを心から願っています。ご質問やフィードバックをお待ちしております。ご質問やコメントがございましたら、お気軽に Twitter までご連絡ください。
-
あなたはおそらくRedisストリームについて間違って考えています
私は個人的にストリームを間違った方法で記述したことで罪を犯しています。私はそれを「単一のキーの下で時間順に並べられた一連のハッシュマップのような要素」と定義しました。 これは正しくありません 。時間とキーに関する最後のビットはOKですが、最初のビットはすべて間違っています。 ストリームが誤解されている理由と、ストリームが実際にどのように動作するかを見てみましょう。この誤解の良い点と悪い点、およびそれがソフトウェアにどのように影響するかを評価します。最後に、RedisStreamsのあまり知られていないプロパティを利用するいくつかの非自明なパターンを調べます。 背景 まず、誤解が始まるX
-
Vercel Edge と Upstash Redis を使用して Next.js にレート制限を実装する
この記事では、Vercel Edge Middleware と @upstash/ratelimit ライブラリを利用して Web アプリケーションにレート制限を実装するプロセスについて説明します。後者は、レート制限データの保存と管理のためにバックエンドで Redis を利用します。 Vercel Edge を使用する利点 Vercel Edge は、ユーザーに最も近い場所で計算を実行するコンピューティング プラットフォームです。リクエストがバックエンドに到達する前にインターセプトする Vercel Edge Middleware を利用します。私は、いくつかの理由から、これがレート制限の実