Forguncy 10 オンラインヘルプ
アプリの開発 / ユーザー管理と保護 / ログインと認証 / カスタムシングルサインオン
このトピックで
    カスタムシングルサインオン
    このトピックで

    Forguncyで作成したアプリケーションで異なるWebアプリケーションやクラウドサービスの認証情報を利用する、いわゆるシングルサインオンを実現する場合、認証プロバイダーの利用を検討してください。

    認証プロバイダーでは実現が不可能な場合、プログラミングによるカスタマイズによってシングルサインオンが可能です。ここでは、そのような場合におけるシングルサインオンの方法を説明します。なお、本機能はWindows認証では使用できません。

    Forguncyの認証連携機能は、以下の図のような流れで行われます。

    1. ユーザーのトークンを要求します。

      ユーザーのトークンを要求するには、以下の仕様を満たしたHTTPリクエストを行います。

      送信先

      http://<サーバー名>/<アプリケーションパス>/SSO/GetUserToken

      HTTPメソッド

      POST

      メッセージボディ

      認証させたいForguncyのユーザー名と認証連携用パスワードを持つJSON

      例)

      {userName:"user1", password:"6s6s6s6s6s6s"}

      上記のメッセージボディに含まれるパスワードは、他のアプリケーションからログインを許可した場合に設定されるアプリケーションで共通のパスワードです。このパスワードは、以下の場所で確認、および変更を行うことが可能です。

      [ファイル]→[オプション]→[アプリケーション連携]を選択して、[他のアプリケーションからのログインを許可する]をチェックします。

      [他のアプリケーションからのログインを許可する]がチェックされていなければ、ユーザーのトークンを要求することはできません。

    2. ユーザートークンを受け取る。

      トークンを要求するHTTPリクエストが成功した場合、そのレスポンスとしてトークンが返されます。トークンを要求するHTTPリクエストが失敗した場合、返されるトークンは「Error:」の文字列から始まります。

    3. トークンをクエリ文字列(URLパラメーター)として指定して、遷移したいForguncyアプリケーションのページに遷移します。

      http://<サーバー名>/<アプリケーションパス>/?token=1h1h1h1h-1h1h-1h1h-1h1h-1h1h1h1h1h1h

      2の手順でトークンを受け取ってから、3の手順を行うまでの制限時間は、既定では10秒に設定されています。これを変更する場合には、以下の手順で行います。

      [ファイル]→[オプション]→[アプリケーション連携]を選択して、[トークンの有効期限]を変更します。

    サンプルコード

    C#の場合のサンプルコードを2つ以下に示します。

    Forguncyアプリケーションが、HTTPS通信もしくは既存アプリケーションで信頼できるネットワークの場合は旧サンプルコードをお使いください。

    C#(旧)
    コードのコピー
        internal class Program
        {
            static HttpClient client = new HttpClient();
            static async Task Main(string[] args)
            {
                var baseUrl = "http://localhost:47054/Forguncy";
                var userName = "administrator";
                var password = "@ddRUvpPgb^6";
    
                var ssoResponse = await client.PostAsync(baseUrl + "/SSO/GetUserToken", JsonContent.Create(new Dictionary
                {
                    {"userName",userName },
                    {"password",password }
                }));
    
                var token = await ssoResponse.Content.ReadAsStringAsync();
    
                if (token.StartsWith("Error:"))
                {
                    Console.WriteLine(token);
                    return;
                }
                var str = baseUrl + "?token=" + token;
            }
        }

    C#(新)
    コードのコピー
       internal class Program
        {
            static HttpClient client = new HttpClient();
            static async Task Main(string[] args)
            {
                var baseUrl = "http://localhost:52839/Forguncy";
                var userName = "administrator";
                var password = "Nk0u1w&yXqwh";
                var publicKeyRespose = await client.PostAsync(baseUrl + "/SSO/GetRSAPublicKey", null);
                var publicKey = await publicKeyRespose.Content.ReadAsStringAsync();
                var encryptPassword = EncryptDataWithPemPublicKey(password, publicKey);
                var ssoResponse = await client.PostAsync(baseUrl + "/SSO/GetUserToken", JsonContent.Create(new Dictionary
                {
                    {"userName",userName },
                    {"password",encryptPassword },
                    {"publicKey",publicKey },
                }));
                var token = await ssoResponse.Content.ReadAsStringAsync();
                if (token.StartsWith("Error:"))
                {
                    Console.WriteLine(token);
                    return;
                }
                var str = baseUrl + "?token=" + token;
            }
            public static string EncryptDataWithPemPublicKey(string dataToEncrypt, string pemPublicKey)
            {
                using RSA rsa = RSA.Create();
                rsa.ImportFromPem(pemPublicKey.ToCharArray());
                byte[] dataBytes = Encoding.UTF8.GetBytes(dataToEncrypt);
                byte[] encryptedData = rsa.Encrypt(dataBytes, RSAEncryptionPadding.Pkcs1);
                return Convert.ToBase64String(encryptedData);
            }