エンドユーザー認証

コンタクト センター AI プラットフォームは、エンドユーザー認証を使用して、ホストアプリを使用しているユーザーを安全に識別します。このメカニズムにより、承認されたユーザーのみが CCAI Platform API にアクセスでき、チャット セッションとデータが特定の ID に安全に結び付けられます。

エンドユーザーを識別するには、ホストアプリがその特定の人物を表すユニバーサルに一意な識別子(UUID)を提供する必要があります。

CCAI プラットフォームでの認証の仕組み

CCAI Platform の認証は、JSON Web Token(JWT)を使用した安全なハンドシェイクに依存しています。JWT は、情報を JSON オブジェクトとして安全に送信するために使用されるオープン スタンダードです。

標準の認証フローは次のとおりです。

  1. リクエスト: エンドユーザーが CCAI プラットフォームのカスタマー サービスの使用を開始すると、CCAI プラットフォーム SDK はホストアプリから署名付き JWT をリクエストします。

  2. 署名: ホストアプリは、共有 CCAI Platform 企業秘密(company_secret)を使用して JWT に署名します。

  3. 交換: ホストアプリは、署名付き JWT を CCAI Platform SDK に渡します。SDK はこの JWT を CCAI Platform サーバーに送信します。

  4. 検証: CCAI Platform サーバーが署名を検証します。有効な場合、CCAI Platform は認証トークンを発行し、ユーザーに API へのアクセス権を付与して、ユーザーをアカウントに関連付けます(アカウントが存在しない場合は新しいアカウントを作成します)。

ホストアプリが JWT ペイロードで識別子を提供しない場合、CCAI Platform はユーザーの匿名ゲスト アカウントを作成します。

前提条件

認証を実装する前に、一意の SDK 認証要素が必要です。これにより、CCAI Platform API に対して会社が安全に識別されます。

  1. 管理者アカウントで CCAI Platform にログインします。

  2. [設定] > [デベロッパー設定] > [API 認証情報] に移動します。

  3. SDK キー名(sdk_key_name)、SDK キー(sdk_key)、会社の秘密鍵(company_secret)を確認します。

これらの認証情報は安全に保管してください。承認されたシステムとデベロッパーとのみ共有してください。

デベロッパー実装ガイド

次のセクションでは、デベロッパーがさまざまなプラットフォームで JWT ペイロードを構築し、CCAI Platform SDK を初期化する方法について説明します。

JWT ペイロードの要件

エンドユーザーの情報を CCAI プラットフォームに渡すには、ホストアプリで JWT ペイロードを構築する必要があります。コールバック メソッドはデフォルトのペイロード(プッシュ トークンとデフォルト名を含む)を提供しますが、次の予約済みキーを使用して特定のユーザーの詳細を追加できます。

  • identifier(省略可、ただし強く推奨される UUID)

  • name(オプション)

  • email(オプション)

  • phone(省略可、E.164 形式を使用する必要があります)

  • iss(省略可、会社名)

  • iat(必須、発行時のタイムスタンプ)

  • exp(必須、有効期限のタイムスタンプ)

サーバーサイド署名(推奨)

する必要があります。

サーバー上の API の例(Ruby on Rails)

この例では、JWT gem を使用して Ruby on Rails フレームワークでサーバーサイドのペイロードに署名する方法を示します。

このコードは、jwt gem を使用して API エンドポイント(/api/ujet/sign)を設定し、会社のシークレットでペイロードをエンコードして、エンコードされたトークンをクライアントに返します。

ホスト アプリケーションのベース URL が https://company.com/api/ であるとします。CCAI Platform のペイロードに署名するには、https://company.com/api/ujet/sign に別の API エンドポイントを追加します。

このコードは、アプリケーションのルートファイルに新しいルートを追加して、/api/ujet/sign URL への POST リクエストを処理します。

ujet_controller.rb ファイルは、CCAI Platform のペイロードの署名に使用される単一のエンドポイント sign を持つ UjetController クラスを定義します。

コードでは、COMPANY_SECRET はペイロードの署名に使用されるシークレットとして定義されています。ペイロードはリクエストの本文から抽出され、UNIQUE-IDENTIFIER、ユーザー名、メールアドレス、電話番号などのさまざまな値が追加されます。

JWT.encode メソッドは、ペイロードと ujet_secret を JSON Web Token(JWT)にエンコードするために使用されます。この JWT は、トークンキーを含む JSON オブジェクトとしてレスポンスで返されます。

# routes.rb
post 'ujet/sign' => "ujet#sign"

# ujet_controller.rb
class UjetController
  def sign
    # In production, securely store and call your secret (e.g., via environment variables)
    ujet_secret = "COMPANY_SECRET"

    payload = body["payload"]
    payload["identifier"] = "UNIQUE-IDENTIFIER"
    payload["name"] = "user name"
    payload["email"] = "test@email.com"
    payload["phone"] = ""                     # E.164 format
    payload["iss"] = "YOUR_COMPANY_NAME"
    payload["iat"] = Time.now.to_i
    payload["exp"] = Time.now.to_i + 10.minutes # Valid for 10 minutes

    token = JWT.encode(payload, ujet_secret)

    render json: {token: token}
  end
end

クライアントサイドの初期化

次のガイドラインに沿って、CCAI Platform モバイル SDK を初期化します。

iOS SDK からの署名

この iOS SDK からのペイロードの署名の例では、ペイロードをリクエスト本文として、URL https://your.company.com/api/ujet/sign のサーバーに POST リクエストを行います。

サーバーはレスポンスとして署名付きトークンを返すことが想定されています。このトークンは、JSON オブジェクトの「token」キーの形式で成功コールバックに渡されます。

リクエスト中にエラーが発生した場合は、失敗時のコールバックに渡されます。

-   (void)signPayload:(NSDictionary *)payload payloadType:(UjetPayloadType)payloadType success:(void (^)(NSString *))success failure:(void (^)(NSError *))failure
{
  if (payloadType == UjetPayloadAuthToken) {
    NSURLSessionConfiguration *sessionConfiguration = [NSURLSessionConfiguration defaultSessionConfiguration];
    NSURLSession *session = [NSURLSession sessionWithConfiguration:sessionConfiguration];

    NSMutableURLRequest *mutableRequest = [[NSMutableURLRequest alloc] init];
    mutableRequest.URL = [NSURL URLWithString:@"https://your.company.com/api/ujet/sign"];
    mutableRequest.HTTPMethod = @"POST";
    NSError *error;
    NSDictionary *data = @{@"payload": payload};
    mutableRequest.HTTPBody = [NSJSONSerialization dataWithJSONObject:data options:0 error:&error];

    NSURLSessionDataTask *task = [session dataTaskWithRequest:mutableRequest completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
        if(error) {
            failure(error);
        }
        else {
            NSDictionary *json = [NSJSONSerialization JSONObjectWithData:data options:0 error:nil];
            success(json[@"token"]);
        }
    }];

    [task resume];
  }
}

Android SDK から署名する

以下は、Android SDK からペイロードに署名する例です。

この例では、Android 用の HTTP クライアントである Retrofit を使用して、サーバーから署名付きペイロードをリクエストします。この関数は、ペイロード、ペイロード タイプ、トークン コールバックを入力として受け取ります。

ペイロード タイプが UjetPayloadType.AuthToken の場合、Retrofit インスタンスを作成し、それを使用して https://company.com/api API エンドポイントにリクエストを送信してペイロードに署名し、tokenCallback インスタンスの onToken メソッドで署名付きトークンを返します。

失敗した場合は、トースト メッセージ "Authentication failed" を表示します。

public void onSignPayloadRequest(Map<String, Object> payload, UjetPayloadType ujetPayloadType, final UjetTokenCallback tokenCallback) {
    if (ujetPayloadType == UjetPayloadType.AuthToken) {
        Retrofit retrofit = new Retrofit.Builder()
                .baseUrl("https://company.com/api/")
                .addConverterFactory(GsonConverterFactory.create())
                .build();

        AuthService authService = retrofit.create(AuthService.class);
        Call<AuthToken> authenticate = authService.authenticate(new AuthRequest(payload));
        authenticate.enqueue(new Callback<AuthToken>() {
            @Override
            public void onResponse(Call<AuthToken> call, Response<AuthToken> response) {
                if (response.isSuccessful()) {
                    AuthToken authToken = response.body();
                    tokenCallback.onToken(authToken.getToken());
                } else {
                    Toast.makeText(ExampleApplication.this, "Authentication failed", Toast.LENGTH_SHORT).show();
                }
            }

            @Override
            public void onFailure(Call<AuthToken> call, Throwable t) {
                Toast.makeText(ExampleApplication.this, "Authentication failed", Toast.LENGTH_SHORT).show();
            }
        });
    }
}

ウェブ SDK からの署名

次の例は、ペイロードを使用してサーバーに API リクエストを行うことで、Web SDK でペイロードに署名する方法を示しています。

サーバーは、API リクエストを処理し、安全な方法でペイロードに署名するように設定する必要があります。結果はウェブページに返され、ウェブページはコールバック関数を使用して署名付きトークンを CCAI Platform に返します。

$(function() {
  UJET.initialize({
    // ... other parameters
    handlers: {
      authentication(callback) {
        $.ajax({
          type: 'POST',
          url: 'https://company.com/api/ujet/sign',
          data: JSON.stringify({
            payload: {
              identifier: 'UNIQUE-Identifier',
              name: 'Test user'
            }
          }),
          success: function(result) {
            callback({
              token: result.token,
              user: {
                identifier: 'UNIQUE-IDENTIFIER',
                name: 'Test user'
              }
            });
          }
        });
      }
    }
  }).then(function() {
    // successfully initialized
  }).catch(function(error) {
    // Handle initialization error
  });
});

セッション中の認証と SDK の再初期化

エンドユーザーがゲスト(未認証)としてチャット セッションを開始し、セッションの途中で(仮想アシスタントやフロー内のログイン画面などを使用して)本人確認を行う場合があります。アクティブなセッションが安全に更新され、新しく認証されたユーザーに関連付けられるようにするには、次の手順を行います。

セッション中の認証の手順

  1. 一時的な識別子を使用して SDK を初期化する: ユーザーが認証されていない場合は、ランダムな識別子またはゲスト識別子を使用して CCAI Platform SDK を初期化します。

  2. ユーザーを認証に誘導する: CCAI Platform の仮想アシスタント(VA)やアプリの組み込みログイン画面など、認証フローにユーザーを誘導します。

  3. API を介してエンドユーザーを更新する: ユーザーが認証に成功したら(仮想エージェントまたは認証フローにいる間)、バックエンドで CCAI Platform Apps API を呼び出して、エンドユーザーのチャット セッションを実際の識別子で更新する必要があります。

  4. 新しい JWT で SDK を再初期化する: バックエンドの更新が成功したら、認証済みユーザーの新しい JWT を生成します。この新しい JWT を使用して初期化メソッドを再度呼び出し、CCAI Platform SDK を再初期化します。

  5. セッションをエスカレーションする(VA を使用している場合): ユーザーが仮想アシスタントを使用して認証を行っていた場合、仮想エージェントはユーザーを最終的な宛先キューにエスカレーションします。

例(ウェブ SDK)

再初期化するには、UJET.initialize 関数をもう一度呼び出します。これにより、認証ハンドラがトリガーされ、新しいトークンが取得されます。

// Call this after successful authentication and the CCAI Platform Apps API update
UJET.initialize({
  // ...include your existing parameters
  handlers: {
    authentication(callback) {
      // Fetch the new JWT for the newly authenticated user
      $.ajax({
        type: 'POST',
        url: 'https://your.company.com/api/ujet/sign',
        data: JSON.stringify({
          payload: {
            identifier: 'AUTHENTICATED-USER-UUID',
            name: 'Authenticated User Name'
          }
        }),
        success: function(result) {
          callback({
            token: result.token,
            user: {
              identifier: 'AUTHENTICATED-USER-UUID',
              name: 'Authenticated User Name'
            }
          });
        }
      });
    }
  }
}).then(function() {
  // SDK successfully reinitialized with the authenticated user
}).catch(function(error) {
  // Handle reinitialization errors
});

なぜこの設定が必要なのですか?

  • これにより、後続のすべてのアクション、ルーティング、履歴が、匿名のゲスト セッションではなく、認証済みユーザーに安全に関連付けられます。

  • データ漏洩を防ぎ、正確な CRM とユーザーの記録を維持できます。

サマリー テーブル

シナリオ 対応が必要
ユーザーが認証済みで開始する ユーザーの実際の UUID と JWT を使用して SDK を初期化します。
ユーザーが認証されていない状態で開始する ゲスト/ランダム ID で SDK を初期化します。
セッション中にユーザーが認証される API で CCAI Platform を更新し、新しい JWT を生成して、SDK を再初期化します。