ホームページ >ウェブフロントエンド >jsチュートリアル >Permit.io と WebSocket を使用したチャット アプリケーションでのリアルタイム認証

Permit.io と WebSocket を使用したチャット アプリケーションでのリアルタイム認証

Patricia Arquette
Patricia Arquetteオリジナル
2025-01-23 18:41:09658ブラウズ

最新のチャット アプリケーションが進化するにつれて、リアルタイム通信にはますます詳細なアクセス制御が必要になります。さまざまなチャット ルームや参加者に対する動的な権限をリアルタイムで管理することは、特に複雑な環境やマルチユーザー環境では、すぐに困難になる可能性があります。パフォーマンスを損なうことなく、チャット アプリにきめ細かい承認を簡単に実装できたらどうでしょうか?

Permit.io を使用すると、堅牢なリアルタイムのアクセス制御をチャット アプリケーションに簡単に統合できます。 Permit.io の高度な認証モデルと WebSocket を組み合わせることで、チャット アプリケーションに必要な応答性を維持しながら、適切なユーザーが適切なタイミングでアクセスできるようになります。

このチュートリアルでは、Permit.io を使用して WebSocket ベースのチャット アプリケーションにリアルタイム認証を実装する方法を学習します。最後には、役割ベースおよび属性ベースのアクセス制御を動的に適用し、さまざまなチャット ルーム、メッセージの可視性、およびリアルタイムの対話を保護する方法を理解できるようになります。

チャット アプリケーションでのリアルタイム認証の概要

私たちは皆、友人や家族と連絡を取り合ったり、同僚と重要な問題について話し合ったり、ビジネスを行ったりするために、何らかの形でチャット アプリケーションを使用しています。シームレスなリアルタイム通信への需要が高まるにつれ、これらのやり取りを保護する高度なセキュリティ対策が当然のことと思われがちです。ただし、チャット アプリケーションが複雑になるにつれて、ユーザー データと会話のセキュリティを確保するという課題も複雑になります。きめ細かいアクセス制御により、許可されたユーザーのみが機密情報やアクションにアクセスできるようになります。

リアルタイム チャット アプリにはなぜきめ細かいアクセス制御が必要なのか

リアルタイム チャット アプリケーションでは、セキュリティ、ユーザーのカスタマイズ、規制順守を確保するために、きめ細かいアクセス制御が不可欠です。
チャット アプリケーションは、堅牢な認証方法とロールベースの権限を設定することで、権限のないユーザーが機密の会話にアクセスすることを防ぎ、管理者がユーザーのやり取りを効果的に管理できるようにします。このアプローチでは、個人の役割や設定に基づいてさまざまなタイプのチャット (公開、プライベート、またはグループ) に参加できるようになり、より魅力的な対話が生み出されるため、ユーザー エクスペリエンスも向上します。
さらに、きめ細かいアクセス制御により、組織は GDPR などの厳格なデータ プライバシー規制に準拠し、機密データを保護し、法的リスクを最小限に抑えることができます。

チャットコンテキストで動的認可を実装する際の課題

ポイントは、各段落の主要なアイデアをすべてカバーしています。これは、あらゆる詳細を含む洗練されたバージョンです:

  1. リアルタイム チャット アプリでは、即時の権限チェックと更新が必要となるため、特に大量のメッセージやユーザーを処理する場合、パフォーマンスに影響を与える危険を冒さずに動的認証を行うことが困難になります。
  2. チャット アプリケーションには、役割、グループ メンバーシップ、または特定の属性に基づいて権限が異なる複数のアクセス レイヤが含まれることが多く、一貫した効率的な適用が必要です。
  3. 役割の動的な変更 (管理者の昇進、グループの削除、一時的なアクセスなど) は、進行中の会話を中断することなく、すべてのアクティブなセッションにわたって認識され、即座に適用される必要があります。
  4. シームレスなユーザー エクスペリエンスを維持しながらこのレベルの柔軟性を達成するには、WebSocket などのリアルタイム プロトコルと緊密に統合された高度な認証モデルが必要です。

Permit.io の認証ソリューションが WebSocket を使用してこのプロセスを合理化する方法の概要

Permit.io の認証ソリューションは、特に WebSocket と統合された場合に、チャット アプリケーションでのリアルタイム認証の実装を大幅に合理化できます。この組み合わせによって動的アクセス制御がどのように強化されるかの概要を次に示します。

  1. シームレスな統合: Permit.io は、WebSocket を利用してチャット アプリケーションに簡単に統合できる、きめ細かいアクセス制御を管理するための堅牢なフレームワークを提供します。この統合により、リアルタイムの権限チェックと更新が可能になり、ユーザーは自分の役割と属性に基づいて適切なチャット ルームと機能に即座にアクセスできるようになります。
  2. 動的権限管理: Permit.io を使用すると、開発者はユーザーの役割やグループのメンバーシップの変更に適応する動的認可モデルを実装できます。たとえば、ユーザーが管理者ロールに昇格した場合、または一時的に特別なアクセス権が付与された場合、進行中の会話を中断することなく、これらの変更をすべてのアクティブなセッションに即座に反映できます。この機能は、アクセス許可がリアルタイムで一貫して適用されることを保証することで、動的認可における主な課題の 1 つを解決します。
  3. 強化されたパフォーマンス: Permit.io は、通信に WebSocket を利用することで、リアルタイムの認証プロセスがアプリケーションのパフォーマンスを損なうことがないようにします。このアーキテクチャは大量のメッセージとユーザーをサポートし、チャット アプリケーションの重要な要件である応答性を維持しながら、同時アクセス要求を効率的に処理できます。
  4. ロールベースおよび属性ベースのアクセス制御: Permit.io は、チャット環境内でのロールベースと属性ベースの両方のアクセス制御の実施を容易にします。この柔軟性により、管理者はモデレータや通常のユーザーなど、さまざまなユーザー タイプに特定の権限を定義でき、カスタマイズ可能なユーザー エクスペリエンスを提供しながらセキュリティを強化できます。ユーザーは、割り当てられた役割に基づいて、パブリック、プライベート、またはグループなど、さまざまな種類のチャットに参加できます。
  5. 規制遵守: Permit.io のソリューションを導入すると、許可されたユーザーのみがチャット アプリケーション内の機密情報や機能にアクセスできるようになり、組織が厳しいデータ プライバシー規制に準拠できるようになります。このコンプライアンスは、ユーザー データを保護し、不正アクセスに関連する法的リスクを最小限に抑えるために非常に重要です。

WebSocket ベースのチャット アプリケーションのセットアップ

Web ソケットベースのアプリケーションでは、Next.js と、Web ソケットを利用したアプリのリアルタイム機能を簡単に統合して管理できるサービスである Ably を使用します。

Ably と Next Auth に加えて、Firebase などを使用して認証とリアルタイム機能の両方を処理できます。それに関するチュートリアル全体が Permit.io ブログにあります。

早速、先に進みましょう!

Next.js のセットアップ

次のコマンドを実行し、プロンプトに従います:

npx create-next-app@latest live-chat
Need to install the following packages:
create-next-app@15.1.0
Ok to proceed? (y) y

✔ Would you like to use TypeScript? … No / Yes
✔ Would you like to use ESLint? … No / Yes
✔ Would you like to use Tailwind CSS? … No / Yes
✔ Would you like your code inside a `src/` directory? … No / Yes
✔ Would you like to use App Router? (recommended) … No / Yes
✔ Would you like to use Turbopack for `next dev`? … No / Yes
✔ Would you like to customize the import alias (`@/*` by default)? … No / Yes
Creating a new Next.js app in /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat.

Using npm.

Initializing project with template: app-tw 


Installing dependencies:
- react
- react-dom
- next

Installing devDependencies:
- typescript
- @types/node
- @types/react
- @types/react-dom
- postcss
- tailwindcss
- eslint
- eslint-config-next
- @eslint/eslintrc


added 371 packages, and audited 372 packages in 1m

141 packages are looking for funding
  run `npm fund` for details

found 0 vulnerabilities
Initialized a git repository.

Success! Created live-chat at /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat 

新しく作成したプロジェクト フォルダーに移動し、アプリの構築に使用するさらにいくつかのパッケージをインストールします。

npx create-next-app@latest live-chat
Need to install the following packages:
create-next-app@15.1.0
Ok to proceed? (y) y

✔ Would you like to use TypeScript? … No / Yes
✔ Would you like to use ESLint? … No / Yes
✔ Would you like to use Tailwind CSS? … No / Yes
✔ Would you like your code inside a `src/` directory? … No / Yes
✔ Would you like to use App Router? (recommended) … No / Yes
✔ Would you like to use Turbopack for `next dev`? … No / Yes
✔ Would you like to customize the import alias (`@/*` by default)? … No / Yes
Creating a new Next.js app in /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat.

Using npm.

Initializing project with template: app-tw 


Installing dependencies:
- react
- react-dom
- next

Installing devDependencies:
- typescript
- @types/node
- @types/react
- @types/react-dom
- postcss
- tailwindcss
- eslint
- eslint-config-next
- @eslint/eslintrc


added 371 packages, and audited 372 packages in 1m

141 packages are looking for funding
  run `npm fund` for details

found 0 vulnerabilities
Initialized a git repository.

Success! Created live-chat at /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat 

また、Radix UI からいくつかの UI コンポーネントをインストールします。

cd live-chat
npm install -D prettier prettier-plugin-tailwindcss  @tailwindcss/forms 

プロジェクト ディレクトリのルートに新しいファイル - .prettierrc を作成し、次のように入力します。

npm install @radix-ui/react-scroll-area

tailwind.config.ts ファイルに次のように入力します:

{
  "plugins": ["prettier-plugin-tailwindcss"]
}
// ./tailwind.config.ts
import type { Config } from "tailwindcss";
import tailwindForms from "@tailwindcss/forms";
export default {
  content: [
    "./pages/**/*.{js,ts,jsx,tsx,mdx}",
    "./components/**/*.{js,ts,jsx,tsx,mdx}",
    "./app/**/*.{js,ts,jsx,tsx,mdx}",
  ],
  theme: {
    extend: {
      colors: {
        background: "var(--background)",
        foreground: "var(--foreground)",
      },
    },
  },
  plugins: [tailwindForms],
} satisfies Config;

グローバルスタイルを設定する

./app/globals.css ファイルに次のように入力します:

In the `./next.config.ts`, enter the following:

// ./next.config.ts
import type { NextConfig } from "next";
const nextConfig: NextConfig = {
  /* config options here */
  images: {
    remotePatterns: [
      {
        protocol: "https",
        hostname: "lh3.googleusercontent.com",
      },
      {
        protocol: "https",
        hostname: "www.tapback.co",
      },
    ],
  },
};
export default nextConfig;

認証の設定

元々 Next.js 用に構築された認証ライブラリである Auth.js を使用します。
次のコマンドを実行してパッケージをインストールします:

/* ./app/globals.css */
@tailwind base;
@tailwind components;
@tailwind utilities;
@layer base {
  body {
    @apply bg-white text-gray-800 dark:bg-gray-900 dark:text-gray-300;
  }
}
@layer components {
  .btn {
    @apply inline-flex items-center justify-center gap-2 rounded-full bg-gray-100 px-4 py-2 text-sm font-semibold text-gray-500 hover:brightness-95 focus:outline-none focus:ring-2 focus:ring-gray-200 focus:ring-offset-2 dark:bg-gray-800 dark:text-gray-300 dark:brightness-105 dark:hover:bg-gray-700 dark:focus:ring-gray-800 dark:focus:ring-offset-gray-900;
  }
  .btn:has(> .icon:first-child) {
    @apply pl-2;
  }
  .btn:has(> .icon:last-child) {
    @apply pr-2;
  }
  .icon {
    @apply h-5 w-5 text-current;
  }
  .form-input {
    @apply flex grow rounded-full border border-none bg-gray-100 px-4 py-2 text-sm font-semibold text-gray-500 outline-none hover:brightness-95 focus:border-none focus:outline-none focus:ring-2 focus:ring-gray-200 focus:ring-offset-2 dark:bg-gray-800 dark:text-gray-300 dark:brightness-105 dark:hover:bg-gray-700 dark:focus:ring-gray-800 dark:focus:ring-offset-gray-900;
  }
  .site-section {
    @apply py-16 md:py-24;
  }
  .site-section > .wrapper {
    @apply mx-auto max-w-5xl px-4 sm:px-6 lg:px-8;
  }
  .noscroll {
    @apply overflow-auto;
    scrollbar-width: none;
  }
}

AUTH_SECRET 環境変数を作成する必要があります。ライブラリは、このランダムな値を使用して、トークンと電子メール検証ハッシュを暗号化します。 (詳細については、「展開」を参照してください)。公式 Auth.js CLI を実行して生成できます:

npm install next-auth@beta

次に、Auth.js 構成ファイルとオブジェクト - ./auth.js:
を作成します。

npx auth secret

? Created /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat/.env.local with `AUTH_SECRET`.

ルート ハンドラーを ./app/api/auth/[...nextauth]/route.ts に追加します:

// ./auth.ts
import NextAuth from "next-auth";
export const { handlers, signIn, signOut, auth } = NextAuth({
  providers: [],
});

セッションを維持するためにオプションのミドルウェアを追加します。これにより、呼び出されるたびにセッションの有効期限が更新されます - ./middleware.ts:

// ./app/api/auth/[...nextauth]/route.ts

import { handlers } from "@/auth"; // Referring to the auth.ts we just created
export const { GET, POST } = handlers;

Google OAuthの設定

NextAuth は、認証用に複数の OAuth プロバイダーをサポートしています。このチュートリアルでは、Google を使用します。

Google クライアント ID とシークレットを取得するには、Google Cloud コンソールで新しいプロジェクトを設定する必要があります - https://console.cloud.google.com/projectcreate

Google Cloud Console

次に、新しく作成したプロジェクトで、新しい同意画面を設定します。

Consent Screen

同意画面が作成されたら、認証情報を設定できます。サイドバーから 資格情報 に移動します。
認証情報の作成 ボタンをクリックし、ドロップダウンから OAuth クライアント ID を選択します。

Oauth Client ID

次の画面で、Web アプリケーションを選択し、 承認された JavaScript オリジンを入力し、リダイレクト URI を入力します: http://localhost:3000 および http://localhost:3000/api/auth/callback/それぞれグーグルで検索してください。

Create Oauth Client ID

これで、クライアント ID とシークレットが得られます。

Client ID and Secret

値をコピーし、.env ファイルに入力します。

npx create-next-app@latest live-chat
Need to install the following packages:
create-next-app@15.1.0
Ok to proceed? (y) y

✔ Would you like to use TypeScript? … No / Yes
✔ Would you like to use ESLint? … No / Yes
✔ Would you like to use Tailwind CSS? … No / Yes
✔ Would you like your code inside a `src/` directory? … No / Yes
✔ Would you like to use App Router? (recommended) … No / Yes
✔ Would you like to use Turbopack for `next dev`? … No / Yes
✔ Would you like to customize the import alias (`@/*` by default)? … No / Yes
Creating a new Next.js app in /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat.

Using npm.

Initializing project with template: app-tw 


Installing dependencies:
- react
- react-dom
- next

Installing devDependencies:
- typescript
- @types/node
- @types/react
- @types/react-dom
- postcss
- tailwindcss
- eslint
- eslint-config-next
- @eslint/eslintrc


added 371 packages, and audited 372 packages in 1m

141 packages are looking for funding
  run `npm fund` for details

found 0 vulnerabilities
Initialized a git repository.

Success! Created live-chat at /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat 

次に、Auth.js 構成でサインイン オプションとして Google を有効にします。 Google プロバイダーをパッケージからインポートし、Auth.js 構成ファイルで前に設定したプロバイダー配列に渡す必要があります:

cd live-chat
npm install -D prettier prettier-plugin-tailwindcss  @tailwindcss/forms 

サイトヘッダーコンポーネントを作成する

サインイン ボタンとサインアウト ボタンを含むアプリのヘッダーを作成しましょう。新しいファイルを作成します - ./components/Site/Header.tsx:

npm install @radix-ui/react-scroll-area

ここでは、SiteHeader コンポーネントがメイン ナビゲーション バーとして機能します。

ユーザー セッションが存在する場合 (セッション?.ユーザー)、ユーザーのアバター、名前、および「サインアウト」ボタンが表示されます。
それ以外の場合は、「サインイン」ボタンを表示します。Next.js サーバー アクションを使用しているため、それをフォーム内に配置します。

signIn 関数とsignOut 関数は、Next.js のサーバー側で実行するためにサーバー アクション マーカー (「サーバーを使用」) でラップされています。

./app/layout.tsx ファイルに SiteHeader コンポーネントをインポートします。

{
  "plugins": ["prettier-plugin-tailwindcss"]
}

ホームページの ./app/page.tsx で、次のように入力します。

// ./tailwind.config.ts
import type { Config } from "tailwindcss";
import tailwindForms from "@tailwindcss/forms";
export default {
  content: [
    "./pages/**/*.{js,ts,jsx,tsx,mdx}",
    "./components/**/*.{js,ts,jsx,tsx,mdx}",
    "./app/**/*.{js,ts,jsx,tsx,mdx}",
  ],
  theme: {
    extend: {
      colors: {
        background: "var(--background)",
        foreground: "var(--foreground)",
      },
    },
  },
  plugins: [tailwindForms],
} satisfies Config;

これで、次のようになります:

Auth with Google

認証を設定したので、Ably を使用してアプリに WebSocket 機能を追加しましょう。

Ably で WebSocket をセットアップする

開始するには、Ably にサインアップしてから、次のオプションを使用して 新しいアプリを作成します。

  • アプリ名: アプリに意味のある名前を付けます
  • ご希望の言語を選択してください: JavaScript
  • どのような種類のアプリを構築していますか? ライブチャット

Ably App Set up

次の画面で、API キーをコピーします:

Ably API Key

.env ファイルに保存します:

In the `./next.config.ts`, enter the following:

// ./next.config.ts
import type { NextConfig } from "next";
const nextConfig: NextConfig = {
  /* config options here */
  images: {
    remotePatterns: [
      {
        protocol: "https",
        hostname: "lh3.googleusercontent.com",
      },
      {
        protocol: "https",
        hostname: "www.tapback.co",
      },
    ],
  },
};
export default nextConfig;

アプリで、Ably React SDK と JWT 用の jose ライブラリをインストールします。

/* ./app/globals.css */
@tailwind base;
@tailwind components;
@tailwind utilities;
@layer base {
  body {
    @apply bg-white text-gray-800 dark:bg-gray-900 dark:text-gray-300;
  }
}
@layer components {
  .btn {
    @apply inline-flex items-center justify-center gap-2 rounded-full bg-gray-100 px-4 py-2 text-sm font-semibold text-gray-500 hover:brightness-95 focus:outline-none focus:ring-2 focus:ring-gray-200 focus:ring-offset-2 dark:bg-gray-800 dark:text-gray-300 dark:brightness-105 dark:hover:bg-gray-700 dark:focus:ring-gray-800 dark:focus:ring-offset-gray-900;
  }
  .btn:has(> .icon:first-child) {
    @apply pl-2;
  }
  .btn:has(> .icon:last-child) {
    @apply pr-2;
  }
  .icon {
    @apply h-5 w-5 text-current;
  }
  .form-input {
    @apply flex grow rounded-full border border-none bg-gray-100 px-4 py-2 text-sm font-semibold text-gray-500 outline-none hover:brightness-95 focus:border-none focus:outline-none focus:ring-2 focus:ring-gray-200 focus:ring-offset-2 dark:bg-gray-800 dark:text-gray-300 dark:brightness-105 dark:hover:bg-gray-700 dark:focus:ring-gray-800 dark:focus:ring-offset-gray-900;
  }
  .site-section {
    @apply py-16 md:py-24;
  }
  .site-section > .wrapper {
    @apply mx-auto max-w-5xl px-4 sm:px-6 lg:px-8;
  }
  .noscroll {
    @apply overflow-auto;
    scrollbar-width: none;
  }
}

jose and ively をインストールしたら、./app/api/ively/route.ts:
を作成します。

npm install next-auth@beta

ここで何が起こっているのかを詳しく見てみましょう:

  1. JWT トークンの作成: createToken 関数は、ユーザー機能とクライアント ID を含む、Ably と互換性のある JSON Web トークンを生成します。ここでは、トークン内のクレームをエンコードします。これは、*.
  2. と一致する名前を持つトピックでこのクライアントによって発行されたイベントに userClaim が含まれることを意味します。
  3. 動的機能:generateCapability 関数は、特定のチャネルに対するロール (モデレータまたは通常のユーザー) に基づいてユーザーに権限を割り当てます。
  4. ユーザー認証: 認証関数はユーザーのセッションを取得するために使用され、認証されたユーザーのみがトークンをリクエストできるようにします。
  5. 環境変数: ABLY_SECRET_KEY 環境変数は、トークン署名用の Ably API シークレットを安全に保存します。
  6. API レスポンス: ハンドラーはリクエストを処理し、トークンを生成し、それを JSON レスポンスとして返すか、ユーザーが認証されていない場合は空の文字列として返します。

次に、チャット ページに必要なすべてのコンポーネントを構築します。ユーザーから送信された 1 つのメッセージを表示するメッセージ アイテム コンポーネントから始めます。

メッセージアイテムコンポーネント

新しいファイルを作成します - ./components/Message/Item.tsx:

npx create-next-app@latest live-chat
Need to install the following packages:
create-next-app@15.1.0
Ok to proceed? (y) y

✔ Would you like to use TypeScript? … No / Yes
✔ Would you like to use ESLint? … No / Yes
✔ Would you like to use Tailwind CSS? … No / Yes
✔ Would you like your code inside a `src/` directory? … No / Yes
✔ Would you like to use App Router? (recommended) … No / Yes
✔ Would you like to use Turbopack for `next dev`? … No / Yes
✔ Would you like to customize the import alias (`@/*` by default)? … No / Yes
Creating a new Next.js app in /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat.

Using npm.

Initializing project with template: app-tw 


Installing dependencies:
- react
- react-dom
- next

Installing devDependencies:
- typescript
- @types/node
- @types/react
- @types/react-dom
- postcss
- tailwindcss
- eslint
- eslint-config-next
- @eslint/eslintrc


added 371 packages, and audited 372 packages in 1m

141 packages are looking for funding
  run `npm fund` for details

found 0 vulnerabilities
Initialized a git repository.

Success! Created live-chat at /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat 

この MessageItem コンポーネントは、配置に flex-row-reverse を使用して、fromUser プロパティに基づいてレイアウトを動的に調整します。
message.data.avatarUrl から取得した送信者のアバターが表示されます。メッセージ テキスト (message.data.text) とそのタイムスタンプ (message.timestamp) が、ローカライズされた時刻文字列としてフォーマットされて表示されます。
現在のユーザーが送信したメッセージの場合、SVG アイコンでレンダリングされた削除ボタンが条件付きで表示され、message.id を使用して onDelete コールバックをトリガーします。

メッセージリストコンポーネント

新しいファイルを作成します - ./components/Message/List.tsx:

cd live-chat
npm install -D prettier prettier-plugin-tailwindcss  @tailwindcss/forms 

MessageList コンポーネントは、messages.map() ループを使用してメッセージのスクロール可能なリストをレンダリングします。各メッセージは、MessageItem コンポーネントを通じて表示されます。
セッション電子メール (session.data.user.email) とメッセージの clientId を比較することで、メッセージがログイン ユーザーによって送信されたかどうかを識別し、ユーザー メッセージを右揃えの自己終了でスタイル設定します。
各 MessageItem は、そのメッセージと onDelete コールバックを受け取ります。

メッセージ入力コンポーネント

新しいファイルを作成します - ./components/Message/Input.tsx:

npm install @radix-ui/react-scroll-area

MessageInput コンポーネントは、useState を使用してユーザー入力を管理し、onSubmit を介してメッセージを送信し、送信後にフィールドをリセットします。入力フィールド () にはコンテキスト プレースホルダーが表示され、disabled プロパティが true の場合は無効になります。

チャットチャネルリストコンポーネント

新しいファイルを作成します - ./components/Chat/ChannelList.tsx:

npx create-next-app@latest live-chat
Need to install the following packages:
create-next-app@15.1.0
Ok to proceed? (y) y

✔ Would you like to use TypeScript? … No / Yes
✔ Would you like to use ESLint? … No / Yes
✔ Would you like to use Tailwind CSS? … No / Yes
✔ Would you like your code inside a `src/` directory? … No / Yes
✔ Would you like to use App Router? (recommended) … No / Yes
✔ Would you like to use Turbopack for `next dev`? … No / Yes
✔ Would you like to customize the import alias (`@/*` by default)? … No / Yes
Creating a new Next.js app in /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat.

Using npm.

Initializing project with template: app-tw 


Installing dependencies:
- react
- react-dom
- next

Installing devDependencies:
- typescript
- @types/node
- @types/react
- @types/react-dom
- postcss
- tailwindcss
- eslint
- eslint-config-next
- @eslint/eslintrc


added 371 packages, and audited 372 packages in 1m

141 packages are looking for funding
  run `npm fund` for details

found 0 vulnerabilities
Initialized a git repository.

Success! Created live-chat at /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat 

ChatChannelList コンポーネントは、チャネルのリストをリンクとしてレンダリングします。アクティブなチャネルは、現在のパス名に基づいて太字のクラスを使用して強調表示されます。

チャットコンポーネント

新しいファイルを作成します - ./components/Chat/index.tsx:

cd live-chat
npm install -D prettier prettier-plugin-tailwindcss  @tailwindcss/forms 

このコンポーネントでは、いくつかのことを行っています。

  1. メッセージ処理: コンポーネントは useChannel 経由でメッセージ (ADD、DELETE、PROMOTE) をリッスンし、それに応じてメッセージ リストを更新します。
  2. メッセージの公開: メッセージは、publishMessage 関数を使用して公開され、メッセージ テキストとユーザー アバターが送信されます。
  3. ScrollArea: Radix UI の ScrollArea は、メッセージ履歴を垂直方向と水平方向の両方にスムーズにスクロールするために使用されます。
  4. メッセージ履歴の取得: マウント時に、チャネルの履歴から最後の 100 メッセージを取得します。

次に、チャット ページにすべてをまとめます。

チャットページの作成

新しいファイルを作成します - ./app/chat/[[...channel]]/page.tsx:

npm install @radix-ui/react-scroll-area

ページ コンポーネントは、状態とコンテキストを管理するプロバイダーでチャット アプリをラップします。 SessionProvider はユーザーのセッションへのグローバル アクセスを保証し、AblyProvider と ChannelProvider はリアルタイム クライアント (authUrl: "/api/ively") と現在のチャンネル名 (例: chat:general) を共有することで、Ably とのシームレスな統合を可能にします。

レイアウトでは、3 つのセクションを持つグリッドを使用します: 左側のサイドバー (チャネル ナビゲーション用 )、中央エリア (メッセージ用 )、および右側のプレースホルダーオンライン ユーザーなどの将来の機能に関するサイドバー (TODO: ユーザー リスト)。 autoConnect オプションを使用すると、Ably がブラウザ内でのみ接続するようになり、SSR の問題が回避されます。

これで、http://localhost:3000/chat/general:

に移動すると、次のようになります。

Chat Interface

さあ、私たちのチャ

Permit.io をセットアップする

https://www.permit.io/ で新しいアカウントを作成します:

Create Permit Account

新しいプロジェクトを作成する

プロジェクトの名前を入力してください。この例では ライブ チャット を使用します:

Create Permit Project

新しいリソースを作成する

チャット アプリのチャネルを作成するには、Permit を使用して、ユーザーがアクセスできるものを表すエンティティであるリソースを作成できます。次に進むためのリソースとしてチャネルを設定しましょう。

Create new resource

リソースの編集

これで、リソースを編集し、チャネル リソースにロールを追加できるようになります:

Edit Resource

役割を表示する

作成したロールは次のとおりです。 ポリシーページのロールタブに移動すると表示できます。

View Roles

ポリシーの更新

これで、ポリシーを更新して、誰が各リソースの何にアクセスできるかを決定できるようになりました。

Update Policies

リソースインスタンスの作成

チャットに必要な各チャネルのリソース インスタンスを作成します。ここでは general チャネルのインスタンスを作成しています。randommod.

Create Resource Instance

インスタンスの表示

ここで、作成されたリソース インスタンスを確認できます:

View Instance

Permit ダッシュボードを設定したので、Next.js アプリに Permit を追加できます。

Next.js アプリケーションに Permit.io を追加する

早速、Permit.io をアプリケーションに統合してみましょう。

まず、permitio パッケージをインストールする必要があります:


npx create-next-app@latest live-chat
Need to install the following packages:
create-next-app@15.1.0
Ok to proceed? (y) y

✔ Would you like to use TypeScript? … No / Yes
✔ Would you like to use ESLint? … No / Yes
✔ Would you like to use Tailwind CSS? … No / Yes
✔ Would you like your code inside a `src/` directory? … No / Yes
✔ Would you like to use App Router? (recommended) … No / Yes
✔ Would you like to use Turbopack for `next dev`? … No / Yes
✔ Would you like to customize the import alias (`@/*` by default)? … No / Yes
Creating a new Next.js app in /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat.

Using npm.

Initializing project with template: app-tw 


Installing dependencies:
- react
- react-dom
- next

Installing devDependencies:
- typescript
- @types/node
- @types/react
- @types/react-dom
- postcss
- tailwindcss
- eslint
- eslint-config-next
- @eslint/eslintrc


added 371 packages, and audited 372 packages in 1m

141 packages are looking for funding
  run `npm fund` for details

found 0 vulnerabilities
Initialized a git repository.

Success! Created live-chat at /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat 
Permit.io ダッシュボードから API キーを取得する必要があります:

Obtain API Key

コピーしたキーを .env ファイルに追加します:


cd live-chat
npm install -D prettier prettier-plugin-tailwindcss  @tailwindcss/forms 
ローカル PDP をセットアップする

次に、ポリシー決定ポイントを設定する必要があります。これは、ポリシーとコンテキスト データを使用して認可クエリに応答する役割を担うネットワーク ノードです。

Docker Hub から PDP コンテナをプルします (ここをクリックして Docker をインストールします):


npm install @radix-ui/react-scroll-area
コンテナを実行し、PDP_API_KEY 環境変数を API キーに置き換えます。


{
  "plugins": ["prettier-plugin-tailwindcss"]
}
PDP のセットアップが完了したので、アプリへの自動追加について詳しく見ていきましょう。Permit.io のこのステップバイステップのチュートリアルから、Next.js アプリへの Permit.io の追加について詳しく学ぶことができます。ブログ。

この例では、いくつかの再利用可能な関数とルートを設定する必要があります。まず、./lib/permit.ts に Permit ライブラリ関数を作成します。

npx create-next-app@latest live-chat
Need to install the following packages:
create-next-app@15.1.0
Ok to proceed? (y) y

✔ Would you like to use TypeScript? … No / Yes
✔ Would you like to use ESLint? … No / Yes
✔ Would you like to use Tailwind CSS? … No / Yes
✔ Would you like your code inside a `src/` directory? … No / Yes
✔ Would you like to use App Router? (recommended) … No / Yes
✔ Would you like to use Turbopack for `next dev`? … No / Yes
✔ Would you like to customize the import alias (`@/*` by default)? … No / Yes
Creating a new Next.js app in /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat.

Using npm.

Initializing project with template: app-tw 


Installing dependencies:
- react
- react-dom
- next

Installing devDependencies:
- typescript
- @types/node
- @types/react
- @types/react-dom
- postcss
- tailwindcss
- eslint
- eslint-config-next
- @eslint/eslintrc


added 371 packages, and audited 372 packages in 1m

141 packages are looking for funding
  run `npm fund` for details

found 0 vulnerabilities
Initialized a git repository.

Success! Created live-chat at /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat 

すべての許可関連のユーティリティ関数用に ./utils/permit.ts ファイルも作成します。

cd live-chat
npm install -D prettier prettier-plugin-tailwindcss  @tailwindcss/forms 

ユーザーフック

フロントエンドで許可ユーザーを簡単に取得できるようにする useUser フックを作成する必要があります。新しいファイル ./hooks/useUser.ts:
を作成します。

npm install @radix-ui/react-scroll-area

認証中に許可されたユーザーを作成する

サインイン中にユーザーを許可に自動的に追加するには、NextAuth のサインイン コールバックを使用します。コールバック中:

  1. リソース インスタンスの取得: 許可からリソース インスタンスを取得します (デフォルトのワークスペースまたはプロジェクトなど)。
  2. ユーザー データの同期: ユーティリティ関数 (handleSyncUser など) を使用して、Permit でユーザーの情報を作成または更新します。これには、ID、電子メール、名前、役割 (「参加者」など)、および関連するリソース インスタンスが含まれます。
  3. サインインの完了: true を返すことでサインイン プロセスが続行されます。

./auth.ts ファイルを次の更新されたコードで置き換えます:

{
  "plugins": ["prettier-plugin-tailwindcss"]
}

これにより、ユーザーは確実に認証され、アクセス制御のために Permit にシームレスに統合されます。

以下に示すように、ユーザーがサインインすると、そのアカウントが Permit ダッシュボードに追加されます。

Permit.io と WebSocket を使用したチャット アプリケーションでのリアルタイム認証

先に進む前に、さらにいくつかのことを設定する必要があります。アプリの開発時に TypeScript を緩和するための型から始めましょう。新しい ./types/user.ts ファイルを作成し、次の内容を入力します:

// ./tailwind.config.ts
import type { Config } from "tailwindcss";
import tailwindForms from "@tailwindcss/forms";
export default {
  content: [
    "./pages/**/*.{js,ts,jsx,tsx,mdx}",
    "./components/**/*.{js,ts,jsx,tsx,mdx}",
    "./app/**/*.{js,ts,jsx,tsx,mdx}",
  ],
  theme: {
    extend: {
      colors: {
        background: "var(--background)",
        foreground: "var(--foreground)",
      },
    },
  },
  plugins: [tailwindForms],
} satisfies Config;

次に、ユーザー データと権限を取得し、ユーザーを昇格および降格するための API ルートをいくつか作成します。

ユーザーデータの取得

新しいファイルを作成します - ./app/api/permit/getUsers/route.ts:

In the `./next.config.ts`, enter the following:

// ./next.config.ts
import type { NextConfig } from "next";
const nextConfig: NextConfig = {
  /* config options here */
  images: {
    remotePatterns: [
      {
        protocol: "https",
        hostname: "lh3.googleusercontent.com",
      },
      {
        protocol: "https",
        hostname: "www.tapback.co",
      },
    ],
  },
};
export default nextConfig;

ユーザーデータの取得

新しいファイルを作成します *./app/api/permit/getUser/route.ts*:

/* ./app/globals.css */
@tailwind base;
@tailwind components;
@tailwind utilities;
@layer base {
  body {
    @apply bg-white text-gray-800 dark:bg-gray-900 dark:text-gray-300;
  }
}
@layer components {
  .btn {
    @apply inline-flex items-center justify-center gap-2 rounded-full bg-gray-100 px-4 py-2 text-sm font-semibold text-gray-500 hover:brightness-95 focus:outline-none focus:ring-2 focus:ring-gray-200 focus:ring-offset-2 dark:bg-gray-800 dark:text-gray-300 dark:brightness-105 dark:hover:bg-gray-700 dark:focus:ring-gray-800 dark:focus:ring-offset-gray-900;
  }
  .btn:has(> .icon:first-child) {
    @apply pl-2;
  }
  .btn:has(> .icon:last-child) {
    @apply pr-2;
  }
  .icon {
    @apply h-5 w-5 text-current;
  }
  .form-input {
    @apply flex grow rounded-full border border-none bg-gray-100 px-4 py-2 text-sm font-semibold text-gray-500 outline-none hover:brightness-95 focus:border-none focus:outline-none focus:ring-2 focus:ring-gray-200 focus:ring-offset-2 dark:bg-gray-800 dark:text-gray-300 dark:brightness-105 dark:hover:bg-gray-700 dark:focus:ring-gray-800 dark:focus:ring-offset-gray-900;
  }
  .site-section {
    @apply py-16 md:py-24;
  }
  .site-section > .wrapper {
    @apply mx-auto max-w-5xl px-4 sm:px-6 lg:px-8;
  }
  .noscroll {
    @apply overflow-auto;
    scrollbar-width: none;
  }
}

ユーザーの昇格

新しいファイル - ./app/api/permit/promoteUser/route.ts を作成し、次のように入力します。

npm install next-auth@beta

ここには、Permit.io を使用してさまざまなリソース インスタンスで特定のロールをユーザーに割り当てることでユーザーを昇格させる Next.js API ルートがあります。
promoteUser 関数は、現在のユーザーが他のユーザーを昇格する権限を持っているかどうかを確認し、指定されたチャネル上のターゲット ユーザーに「参加者」、「モデレータ」、「管理者」などのロールを割り当てます。
GET 関数は、受信リクエストを処理し、クエリ パラメータを抽出して検証し、リソース インスタンスを取得して、プロモーション プロセスを実行します。問題が発生した場合は、結果を JSON 応答またはエラー メッセージとして返します。

ユーザーを降格する

新しいファイル - ./app/api/permit/demoteUser/route.ts を作成し、次のように入力します。

npx create-next-app@latest live-chat
Need to install the following packages:
create-next-app@15.1.0
Ok to proceed? (y) y

✔ Would you like to use TypeScript? … No / Yes
✔ Would you like to use ESLint? … No / Yes
✔ Would you like to use Tailwind CSS? … No / Yes
✔ Would you like your code inside a `src/` directory? … No / Yes
✔ Would you like to use App Router? (recommended) … No / Yes
✔ Would you like to use Turbopack for `next dev`? … No / Yes
✔ Would you like to customize the import alias (`@/*` by default)? … No / Yes
Creating a new Next.js app in /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat.

Using npm.

Initializing project with template: app-tw 


Installing dependencies:
- react
- react-dom
- next

Installing devDependencies:
- typescript
- @types/node
- @types/react
- @types/react-dom
- postcss
- tailwindcss
- eslint
- eslint-config-next
- @eslint/eslintrc


added 371 packages, and audited 372 packages in 1m

141 packages are looking for funding
  run `npm fund` for details

found 0 vulnerabilities
Initialized a git repository.

Success! Created live-chat at /Users/miracleio/Documents/writing/permit/real-time-authorization-in-a-chat-application-with-permitio-and-websockets/live-chat 

同様に、Permit.io を使用して特定のリソース インスタンスに対するユーザーのロールの割り当てを解除することで、ユーザーを降格する Next.js API ルートがあります。 demoteUser 関数は、指定されたチャネル上のユーザーから「参加者」、「モデレーター」、「管理者」などの役割を削除します。 GET 関数は、受信リクエストを処理し、クエリ パラメータを抽出して検証し、リソース インスタンスをフェッチし、ユーザーに割り当てられたロールを取得し、降格プロセスを実行します。

リソースを取得する

新しいファイル ./app/api/permit/listResourceInstances/route.ts を作成し、次のように入力します。

cd live-chat
npm install -D prettier prettier-plugin-tailwindcss  @tailwindcss/forms 

Ably 権限ルートを更新する

ファイル ./app/api/ively/route.ts を次の更新されたコードに置き換えます。

npm install @radix-ui/react-scroll-area

ここでは、ロールと権限を管理するために Permit.io を組み込み、静的な構成を動的なロールベースの権限に置き換えます。
generatePermissions 関数は、Permit.io からのデータを使用してロールを特定のチャネル機能にマッピングし、アクセス許可がユーザーのロールとリアルタイムで一致するようにします。このアプローチにより柔軟性が向上し、ロールや権限の変更にシステムが確実に適応し、Ably の JWT ベースの認証とシームレスに統合されます。

チャンネルリストの更新

許可ダッシュボードにリソース (チャネル) を追加したので、ハードコーディングする代わりにそこから取得できるようになります。
./components/Chat/ChannelList.tsx ファイルで、次の変更を加えます:

{
  "plugins": ["prettier-plugin-tailwindcss"]
}

ユーザーリストの作成コンポーネント

すべての許可ユーザーを取得し、ユーザー名の横に 昇格 または 降格 ボタンを表示するユーザー リスト コンポーネントを作成しましょう。
新しいファイル - ./components/Chat/UserList.tsx を作成し、次の内容を入力します:

// ./tailwind.config.ts
import type { Config } from "tailwindcss";
import tailwindForms from "@tailwindcss/forms";
export default {
  content: [
    "./pages/**/*.{js,ts,jsx,tsx,mdx}",
    "./components/**/*.{js,ts,jsx,tsx,mdx}",
    "./app/**/*.{js,ts,jsx,tsx,mdx}",
  ],
  theme: {
    extend: {
      colors: {
        background: "var(--background)",
        foreground: "var(--foreground)",
      },
    },
  },
  plugins: [tailwindForms],
} satisfies Config;

ここでは、カスタム フック useUser を使用して現在のユーザーの情報を取得し、リアルタイム チャネル通信のために Ably から useChannel フックを取得します。 getUserList 関数は、Permit.io API を使用してサーバーからユーザーのリストを取得します。このコンポーネントはリアルタイム更新のために Ably チャネルをサブスクライブし、昇格/降格イベントが発生したときに更新されたユーザー リストを取得します。ユーザーリストは、現在のユーザーを除き、コンポーネントの状態に保存されます。

最後に、./app/chat/[[...channel]]/page.tsx でページに追加できます:

In the `./next.config.ts`, enter the following:

// ./next.config.ts
import type { NextConfig } from "next";
const nextConfig: NextConfig = {
  /* config options here */
  images: {
    remotePatterns: [
      {
        protocol: "https",
        hostname: "lh3.googleusercontent.com",
      },
      {
        protocol: "https",
        hostname: "www.tapback.co",
      },
    ],
  },
};
export default nextConfig;

これにより、リアルタイムでユーザーを昇格および降格できるようになります:

Real Time Permit.io と WebSocket を使用したチャット アプリケーションでのリアルタイム認証

実際の降格は次のとおりです:

Permit.io と WebSocket を使用したチャット アプリケーションでのリアルタイム認証tion Action

終わりと結論

リアルタイム認証を備えたチャット アプリケーションの構築は、困難ですがやりがいのあるプロセスです。 Permit.io や WebSockets などの強力なツールを統合することで、安全できめ細かいアクセス制御を保証するシームレスなエクスペリエンスを作成できます。この記事では、チャット アプリケーションにおける動的承認の重要性を検討し、Ably で WebSocket ベースのアーキテクチャを設定し、承認管理のために Permit.io を統合しました。

このワークフローは、かつては複雑だった実装が最新のツールによってどのように簡素化され、開発者が基盤となるインフラストラクチャではなくユーザー エクスペリエンスとスケーラビリティに重点を置くことができるかを示しています。適切なアプローチを使用すれば、チャット アプリケーションが動的かつ安全であることを保証できます。

詳細な資料とリソース

  • GitHub コード - https://github.com/miracleonyenma/live-chat
  • Permit.io ドキュメント – Permit.io の機能と API に関する包括的なガイド。
  • Ably WebSockets ドキュメント – Ably を使用したリアルタイム アプリの構築について詳しく説明します。
  • Next.js ドキュメント – Next.js を使用して React アプリケーションを構築するための高度な機能を探索します。
  • Auth.js ドキュメント – Next.js アプリで安全でスケーラブルな認証をセットアップします。
  • リアルタイム Web アプリケーションのための WebSocket – WebSocket とそのユースケースの詳細な概要。

次のステップ

基本的なセットアップが完了すると、次のようなシンプルな機能と高度な機能を探索できます。

  • モデレータが参加者のメッセージを削除できるようにする
  • チャット内の不正なコンテンツを検出して防止する AI を活用したモデレーション ツールを追加します。許可を得て AI アプリケーションを構築する方法について詳しく学ぶことができます
  • ユーザーのアクティビティとメッセージの傾向を追跡するための分析ダッシュボードを実装します。

以上がPermit.io と WebSocket を使用したチャット アプリケーションでのリアルタイム認証の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。