Redis
 Computer >> コンピューター >  >> プログラミング >> Redis

Upstash Redis Search の紹介:Redis データの強力でスケーラブルな検索

今後 1 ~ 2 週間以内に Upstash Redis Search をリリースする予定ですが、私たちが構築しているものと、なぜそれに興奮しているのかについて、初期の考えをいくつか共有したいと思います。

これを構築する理由

私たちは 2024 年から Upstash Vector を皮切りに検索領域に参入してきました。 Vector によりセマンティック検索の実装が可能になり、その後、Upstash Search でこの製品分野にさらに参入しました。

たとえば、これは、ベクトルベースのセマンティック検索ソリューションである Upstash Search を発表する 2025 年の発表ツイートです 👇

Upstash Redis Search の紹介:Redis データの強力でスケーラブルな検索

そして、検索から学んだことを基にしてさらに改善できると思います。

私たちは既存の検索プロバイダーのほとんどにかなり不満を抱いています。私個人としては、どれもサーバーレス空間にあまり適合しません。 2023 年には AWS Cloudsearch をベースにした独自の検索アプリを構築するほどでした 💀

私たちが望んでいたのは次のようなものでした。

  • Redis は高速であるため、Redis に存在します
  • Upstash Redis SDK と連携
  • 100% タイプセーフです
  • 入力しながらのリアルタイム検索に十分な速度

それで、私たちはそれを構築しています。

Redis API を超えた最初の拡張機能

これは私たちにとって大変なことです。今までは @upstash/redis Redis コマンドのほぼ 1:1 マッピングです。検索は、それを超えた最初の拡張機能です。

私たちは内部で Tantivy を使用しています。これは、Apache Lucene からインスピレーションを受け、Rust で書かれた全文検索エンジンです。速いですね。本当に速いです。また、トークン化、ステミング、あいまい一致、フレーズ クエリ、BM25 スコアリングなど、必要なすべてのプリミティブも提供されます。

目標は、これを SDK と Upstash Redis 自体にネイティブに感じさせることです。 @upstash/redis を使用している場合 現在、検索の追加は、別個の製品ではなく、自然な拡張機能のように感じられるはずです。

タイプセーフなスキーマ ビルダー

私が本当に満足している点の 1 つは、新しいスキーマ ビルダーです。 zod のような API を使用して検索可能なフィールドを定義します。

import { Redis, s } from "@upstash/redis";
 
const redis = Redis.fromEnv();
 
const schema = s.object({
 name: s.string(),
 description: s.string(),
 sku: s.string().noTokenize(),
 brand: s.string().noStem(),
 price: s.number(),
 inStock: s.boolean(),
});
 
const products = await redis.search.createIndex({
 name: "products",
 dataType: "json",
 prefix: "product:",
 schema,
});

.noTokenize().noStem() メソッドを使用すると、テキストの処理方法を制御できます。

  • トークン化 テキストを検索可能な単語に分割します。自然言語には最適ですが、SKU (SKU-12345-BLK など) は壊れます。 ["SKU", "12345", "BLK"] になります )。コード、メール、UUID に対しては無効にしてください。
  • ステミング 単語を原形に変換して、「running」が「run」と一致するようにします。完全一致が必要なブランド名や固有名詞については無効にします。

スキーマはクエリに対する完全な型推論を提供します。存在しないフィールドをクエリしようとすると、TypeScript がそれをキャッチします。スキーマ構文を zod 構文に非常に近づけているため、使い慣れています。

クエリプリミティブ

ほとんどの検索ユースケースをカバーすると思われる 5 つの主要な演算子を使用して開始します。

$smart スマートマッチング

$smart 演算子を使用すると、スマート マッチングが自動的に適用されます。この演算子はそのまま機能するはずであり、初心者が始めるのに最適な方法です。

await products.query({
 filter: {
 name: { $smart: "wirless headphones" },
 },
});

内部では以下が実行されます:

<オル>
  • フレーズの完全一致 (最高のブースト) - 「ワイヤレス ヘッドフォン」が隣接して順番に配置されているドキュメント
  • スロップのあるフレーズ (中ブースト) - 単語が順番に出現するが隣接していない文書 (例:ワイヤレスボーズヘッドフォン)
  • 条件が一致 (中ブースト) - すべての用語を任意の順序で含む文書
  • あいまい一致 (ブーストなし) - 「wireles ヘッドフォン」などのタイプミスのある文書
  • 最後の単語のあいまいな接頭辞 (ブーストなし) - 入力しながら検索するシナリオの場合
  • スコアが結合されて、最も関連性の高い結果が得られます。ほとんどの検索ボックスでは、文字通りこれで十分です。もちろん、この演算子は以下の他のプリミティブ演算子に基づいて構築されているため、自分で実装して設定を試すこともできます。

    $eq 完全に等しいため

    完全一致が必要なフィールドの場合:

    await products.query({
     filter: {
     name: { $eq: "wireless headphones" },
     price: { $eq: 200 },
     },
    });

    $phrase フレーズマッチング用

    単語を隣接して順番に表示する必要がある場合:

    await products.query({
     filter: { description: { $phrase: "noise cancelling" } },
    });

    slop を追加することもできます 間に単語を許可するには:

    await products.query({
     filter: {
     description: {
     $phrase: { value: "wireless headphones", slop: 2 },
     },
     },
    });

    $fuzzy タイプミスを許容するため

    設定可能なタイプミス許容値によるあいまい一致の場合 (例:2 つのタイプミス):

    await products.query({
     filter: { name: { $fuzzy: "headphonse", distance: 2 } },
    });

    $regex パターンマッチング用

    正規表現パターンが必要な場合:

    await products.query({
     filter: { sku: { $regex: "SKU-[0-9]{5}-.*" } },
    });

    注意すべき点が 1 つあります。正規表現は、.noStem() を持つフィールドで最もよく機能します。 ステム化されたテキストは予期されるパターンと一致しないためです。

    特定のフィールドを強化する

    ブーストを適用して、特定の一致の重みを高くすることができます。

    await products.query({
     filter: {
     $and: [
     { name: { $smart: "wireless", $boost: 2 } },
     { description: { $smart: "wireless" } },
     ],
     },
    });

    これにより、名前一致の価値は説明一致の 2 倍になります。これは、タイトル マッチをボディ マッチよりも上位にしたい場合に便利です。

    次は何ですか

    この記事に記載した内容はすべて、まだ変更される可能性があります。私たちはまだエッジを磨き、ドキュメントを書いています。正式リリースは 1 ~ 2 週間以内に行われます。

    でも、一緒に最初に見てみることができるのは本当に素晴らしいことだと思います 👀

    リリース後に検討する可能性のあることがいくつかあります:

    • ベクトル検索の統合 (セマンティック + キーワードのハイブリッド検索)
    • オートコンプリートと提案

    早期アクセスが必要な場合、または質問がある場合は、@joshtriedcoding までご連絡ください。

    読んでいただきありがとうございます 🙌


    1. Redis ZREM –Redisでソートされた設定値から要素を削除する方法

      このチュートリアルでは、キーに格納されている並べ替えられた設定値から1つ以上の指定された要素を削除する方法について学習します。このために、コマンドを使用します– ZREM redis-cliで。 このコマンドは、指定されたキーに格納されているソート済みセットから1つ以上の指定された要素を削除します。ソートされたセットに存在しない指定されたメンバーは無視されます。キーは存在するが、キーに格納されている値が並べ替えられたセットのデータ型ではない場合、エラーが返されます。 redis ZREMコマンドの構文は次のとおりです:- 構文:- redis host:post> ZREM

    2. Astro、Upstash、GitHub を使用して、無料のオープンソース LinkTree の代替を構築する

      この投稿では、itsmy.fyi (LinkTree に代わるオープンソース) が Upstash、Astro、GitHuband Edgio を使用してどのように構築されるかについて説明します。 Upstash は、すべてのユーザーの (CRUD) データの管理に役立ち、CRUD 操作に対して GitHub API と比較して大幅なレート制限を提供し、きめ細かいレート制限を実装しました。 使用するもの Astro (フロントエンドおよびバックエンド) Upstash (レート制限と CRUD オペレーション) GitHub の問題と Webhook (ユーザー プロファイルを管理するた