パスポートを使用してReactアプリを認証するにはどうすればよいですか?

Dycey

Reactアプリを持っています。

Expressサーバーもあります。これを使用passport-samlすると、会社のPingID SSOIdPに対して認証できます。

Reactアプリを取得して、どういうわけかExpressアプリを呼び出して認証したいと思います。

ExpressServerとReactアプリは同じホストで実行されています。

これが私が持っているものです:

// Express App - rendering code pulled out
const express = require('express');
var passport = require('passport');
var Strategy = require('passport-saml').Strategy;
var fs = require('fs')
const bodyParser = require('body-parser');
const cookieParser = require('cookie-parser');
const expressSession = require('express-session');
const app = express();
const port = process.env.PORT || 4005;

passport.use('saml2', new Strategy({
    path: 'http://MYSERVER:4005/assert',
    entryPoint: 'https://sso.connect.pingidentity.com/sso/idp/SSO.saml2?XXXXXXXX',
    issuer: 'MYAPP',
    audience: 'MYAPP',
  },
  function(profile, cb) {
    return cb(null, profile);
  }));

passport.serializeUser(function(user, done) {
  done(null, user);
});

passport.deserializeUser(function(obj, done) {
  done(null, obj);
});

app.use(cookieParser());
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended: true }));
app.use(expressSession({
    secret: '123xyz',
    resave: true,
    saveUninitialized: true 
}));

// Initialize Passport and restore authentication state, if any, from the session.
app.use(passport.initialize());
app.use(passport.session());

app.get('/login/idp', () =>{
    passport.authenticate('saml2')
    console.log('Authentication called');
});

app.get('/login', () =>{
    console.log('Authentication failed, try again');
});

app.post('/assert', 
  passport.authenticate('saml2', { failureRedirect: '/login' }),
  function(req, res) {
    console.log('Authentication succeeded');
    console.log(req.user)
    res.redirect('/');
  });

app.listen(port, () => console.log(`Listening on port ${port}`));

私のReactアプリpackage.jsonには次のものがあります:

{
  ...
  "proxy": "http://localhost:4005/",
  ...
}

おもちゃのCreateReactアプリの概要は次のとおりです。

// Create React App
import React, { useState } from 'react';
import './App.css';

function App() {

  const handleLogin = async e => {
    e.preventDefault();
    const response = await fetch('/login/idp', {
      method: 'GET',
      headers: {
        'Content-Type': 'application/json',
      }
    });
  };

  return (
    <div className="App">
      <form onSubmit={handleLogin}>
        <button type="submit">Login</button>
      </form>
    </div>
  );
}

export default App;

ボタンをクリックすると、コンソールにExpressサーバーのGETがトリガーされたことが表示されますが、Reactクライアントには何も返されません。

行く方法を代理していますか?私には正しいアプローチがありますか?もしそうなら、どうすればExpressアプリからReactアプリに結果を戻すことができますか?

Dycey

私には解決策がありますが、それはひどいハックのようです。しかし、それは機能し、私はこれを一線を越えて取得する必要があります。誰かが改善または代替アプローチを提案することができれば、私は感謝するでしょう。

Passport-SAML SSOを介してユーザーを検証できる基本的なExpressサーバー(4005でホストされている)から始めます。

const express = require('express');
const jwt = require('jsonwebtoken')
const passport = require('passport');
const Strategy = require('passport-saml').Strategy;

require('dotenv').config()
const signature = process.env.SIGNATURE
const expiresIn = process.env.EXPIRESIN

// Simplification: actually there's a db look-up here
// based on req.user in order to get just the id
// but you get the idea
const createToken = user =>
    jwt.sign({ user.email }, signature, { expiresIn: expiresIn })

passport.use('saml2', new Strategy({
    path: 'http://localhost:4005/assert',
    entryPoint: 'https://sso.connect.pingidentity.com/sso/idp/SSO.saml2?idpid=XXXX_YOURVALUEHERE_XXXX',
    issuer: 'XXXX_YOURIDHERE_XXXX',
    audience: 'XXXX_YOURIDHERE_XXXX',
  },
  function(profile, cb) {
    return cb(null, profile);
  }));

passport.serializeUser(function(user, done) {
  done(null, user);
});

passport.deserializeUser(function(obj, done) {
  done(null, obj);
});

// Create a new Express application.
var app = express();
app.use(require('cookie-parser')());
app.use(require('body-parser').urlencoded({ extended: true }));

// Initialize Passport and restore authentication state, if any, from the
// session.
app.use(passport.initialize());

app.get('/login/idp', passport.authenticate('saml2'));

app.post('/assert', 
  passport.authenticate('saml2', 
    { failureRedirect: `http://localhost:3000/?error=unauthenticated` } ),
    function(req, res) {
      const token = createToken(req.user)
      res.redirect(`http://localhost:3000/signinOK?token=${token}`);
    });

app.listen(4005);

次に、Reactsrcフォルダーに、必要なsetupProxy.jsを追加します。

const { createProxyMiddleware } = require('http-proxy-middleware');

module.exports = function(app) {
    app.use(
      '/login',
      createProxyMiddleware({
        target: 'http://localhost:4005',
        headers: {
            "Connection": "keep-alive"
        }
      })
    );
  };

次に、Reactアプリ(ポート3000でホストされている)で、フロントページ用のシンプルなボタンコンポーネントを作成します。

import React from 'react'
import { Button } from '@material-ui/core'

function StartBtn() {
  return (
    <Button type="submit" variant="contained" color="primary" >
      <a href="/login/idp">Login</a>
    </Button>
  )
}

export default StartBtn

この時点で<StartBtn />、フロントページに貼り付け、http://localhost:3000/signinOK?token=...トークンを取得して後続のbearer:認証の値として使用し、メインサイトにリダイレクトすることで、応答するルートを設定します。

フローは次のとおりです。

  1. ユーザーがフロントページを読み込み、<StartBtn/>;をクリックします。
  2. setupProxy.jsExpressサーバーのおかげでリンクがリダイレクトされます。
  3. ExpressサーバーはPassport-SAML認証を試みます
  4. 認証プロセスの結果は、/assertルート上のIdP(PingID認証サーバー)からExpressサーバーへのPOST呼び出しです。
  5. 結果は成功または失敗しますが、どちらの場合もReactアプリにリダイレクトされます。
  6. 成功した場合、ユーザーの詳細はJWTとして返されます。または
  7. 失敗した場合、エラーが返されます。

それを改善する方法を見つけることができれば、またはJWTステージで拡張できる場合は、この回答に戻ります。

誰かが(a)これが便利だと思うか、(b)タイムマシンを発明して、3週間前に戻って投稿し、残りの毛包をもっと節約できるようになることを願っています。または(c)私がそれをすべきだった方法を教えてくれます。

この記事はインターネットから収集されたものであり、転載の際にはソースを示してください。

侵害の場合は、連絡してください[email protected]

編集
0

コメントを追加

0

関連記事

分類Dev

基本認証を使用してRailsアプリの統合ミニテストコードを作成するにはどうすればよいですか?

分類Dev

認証されたルートと認証されていないルートがある場合、Expressを使用してreactアプリをクライアントに送信するにはどうすればよいですか?

分類Dev

Rails REST APIアプリでDeviseを使用して認証するにはどうすればよいですか?

分類Dev

アプリが使用しているポートを確認して、ufwで有効にするにはどうすればよいですか?

分類Dev

node.jsでデータとベアラ認証を使用してPOSTリクエストを送信するにはどうすればよいですか?

分類Dev

スクリプトを使用して認証コードフォームgithubを取得するにはどうすればよいですか?

分類Dev

シリアルポートを使用しているかどうかを確認するにはどうすればよいですか?

分類Dev

react-railsを使用してRails 5アプリにreact-routerサポートを追加するにはどうすればよいですか

分類Dev

create reactアプリを使用して特定のReactコンポーネントに画像を表示するにはどうすればよいですか?

分類Dev

React JSを使用してマテリアルUIコンポーネントのラッパーを作成するにはどうすればよいですか?

分類Dev

ホストされているBlazorWebAssemblyアプリを提供する前に、Azure AD B2Cを使用してサーバー上のユーザーを認証するにはどうすればよいですか?

分類Dev

Visual StudioでOpenCVサポートを使用してアプリケーションをコンパイルするにはどうすればよいですか?

分類Dev

スクリプトタグを使用してリモートReactアプリを提供するにはどうすればよいですか?

分類Dev

公開鍵認証を使用せずに、パスワードのプロンプトなしでrsyncするにはどうすればよいですか?

分類Dev

Laravel JWT認証を使用してユーザーにルートへのアクセスを許可するにはどうすればよいですか?

分類Dev

アップロード証明書を使用してアプリの更新をリリースするにはどうすればよいですか?

分類Dev

Empathyで2段階認証プロセスを使用してGmailアカウントを追加するにはどうすればよいですか?

分類Dev

Github:SecurIDデスクトップアプリケーションを2要素認証に使用するにはどうすればよいですか?

分類Dev

sshクライアントにパスワード認証のみを使用するように強制するにはどうすればよいですか?

分類Dev

React.jsアプリで「構成不可能なプロパティ「ChoiceGroupOption」を解決するにはどうすればよいですか。Parcelを使用しており、「office-ui-fabric-react」からcompをインポートしています。

分類Dev

アプリケーションIDとそのキーの1つを使用して認証するにはどうすればよいですか?

分類Dev

Laravel認証を使用しているときにユーザーがreactコンポーネントに「ログイン」しているかどうかを確認するにはどうすればよいですか?

分類Dev

すでにecho "password"を使用して認証に自動合格している場合、プログラムをインストールするための "yes"応答をスクリプト化するにはどうすればよいですか。

分類Dev

トークン認証を使用してPOST / GET curlリクエストを作成するにはどうすればよいですか?

分類Dev

SwiftとiOSを使用してFacebook認証を使用してユーザーをログアウトするにはどうすればよいですか?

分類Dev

シェルスクリプトからマシン上で特定のポートが開いているかどうかを確認し、それに基づいてアクションを実行するにはどうすればよいですか?

分類Dev

Android Studioでデバッグステートメントを生成しているアプリを確認するにはどうすればよいですか?

分類Dev

WPFで、パスマークアップ構文を使用して複合ジオメトリを描画するにはどうすればよいですか?

分類Dev

どのアプリケーションがどのポートを使用しているかを知るにはどうすればよいですか?

Related 関連記事

  1. 1

    基本認証を使用してRailsアプリの統合ミニテストコードを作成するにはどうすればよいですか?

  2. 2

    認証されたルートと認証されていないルートがある場合、Expressを使用してreactアプリをクライアントに送信するにはどうすればよいですか?

  3. 3

    Rails REST APIアプリでDeviseを使用して認証するにはどうすればよいですか?

  4. 4

    アプリが使用しているポートを確認して、ufwで有効にするにはどうすればよいですか?

  5. 5

    node.jsでデータとベアラ認証を使用してPOSTリクエストを送信するにはどうすればよいですか?

  6. 6

    スクリプトを使用して認証コードフォームgithubを取得するにはどうすればよいですか?

  7. 7

    シリアルポートを使用しているかどうかを確認するにはどうすればよいですか?

  8. 8

    react-railsを使用してRails 5アプリにreact-routerサポートを追加するにはどうすればよいですか

  9. 9

    create reactアプリを使用して特定のReactコンポーネントに画像を表示するにはどうすればよいですか?

  10. 10

    React JSを使用してマテリアルUIコンポーネントのラッパーを作成するにはどうすればよいですか?

  11. 11

    ホストされているBlazorWebAssemblyアプリを提供する前に、Azure AD B2Cを使用してサーバー上のユーザーを認証するにはどうすればよいですか?

  12. 12

    Visual StudioでOpenCVサポートを使用してアプリケーションをコンパイルするにはどうすればよいですか?

  13. 13

    スクリプトタグを使用してリモートReactアプリを提供するにはどうすればよいですか?

  14. 14

    公開鍵認証を使用せずに、パスワードのプロンプトなしでrsyncするにはどうすればよいですか?

  15. 15

    Laravel JWT認証を使用してユーザーにルートへのアクセスを許可するにはどうすればよいですか?

  16. 16

    アップロード証明書を使用してアプリの更新をリリースするにはどうすればよいですか?

  17. 17

    Empathyで2段階認証プロセスを使用してGmailアカウントを追加するにはどうすればよいですか?

  18. 18

    Github:SecurIDデスクトップアプリケーションを2要素認証に使用するにはどうすればよいですか?

  19. 19

    sshクライアントにパスワード認証のみを使用するように強制するにはどうすればよいですか?

  20. 20

    React.jsアプリで「構成不可能なプロパティ「ChoiceGroupOption」を解決するにはどうすればよいですか。Parcelを使用しており、「office-ui-fabric-react」からcompをインポートしています。

  21. 21

    アプリケーションIDとそのキーの1つを使用して認証するにはどうすればよいですか?

  22. 22

    Laravel認証を使用しているときにユーザーがreactコンポーネントに「ログイン」しているかどうかを確認するにはどうすればよいですか?

  23. 23

    すでにecho "password"を使用して認証に自動合格している場合、プログラムをインストールするための "yes"応答をスクリプト化するにはどうすればよいですか。

  24. 24

    トークン認証を使用してPOST / GET curlリクエストを作成するにはどうすればよいですか?

  25. 25

    SwiftとiOSを使用してFacebook認証を使用してユーザーをログアウトするにはどうすればよいですか?

  26. 26

    シェルスクリプトからマシン上で特定のポートが開いているかどうかを確認し、それに基づいてアクションを実行するにはどうすればよいですか?

  27. 27

    Android Studioでデバッグステートメントを生成しているアプリを確認するにはどうすればよいですか?

  28. 28

    WPFで、パスマークアップ構文を使用して複合ジオメトリを描画するにはどうすればよいですか?

  29. 29

    どのアプリケーションがどのポートを使用しているかを知るにはどうすればよいですか?

ホットタグ

アーカイブ