OAuth2を使用してユーザーを認証する
OAuth 2.0の認証プロトコルを使用してLiferayのヘッドレスREST APIにアクセスするアプリケーションを作成できます。 提供されているサンプルReactアプリは、OAuth2トークンベースの3種類の認証フロー(認証コードフロー、クライアント認証情報フロー、パスワードフロー)のデモを実行しています。 OAuth2 管理パネルの詳細については、 OAuth2 アプリケーションの作成 を参照してください。
Liferay DXP をセットアップする
Liferay DXP の新しいインスタンスを起動するには、以下を実行します。
docker run -it -m 8g -p 8080:8080 liferay/dxp:2026.q1.9-lts
http://localhost:8080 に、メールアドレス test@liferay.com とパスワード test を使用して Liferay にサインインします。 プロンプトが表示されたら、パスワードを learn に変更してください。
-
グローバルメニュー (
) を開き、 コントロールパネル → セキュリティ → OAuth 2 管理 に移動します。 -
新規 をクリックしてください。
-
アプリケーションに名前を付けてください(例:foo)。 ウェブサイトの URL を
http://localhost:3000に、コールバック URI をhttp://localhost:3000/grant-type-authorization-codeに設定します。 をクリックして保存します。
-
クライアントIDとクライアントシークレットをクリップボードにコピーしてください。 クライアントシークレットを取得するには、 編集 をクリックしてください。 ポップアップウィンドウから値をコピーしてください。
これらの値は、後ほどサンプルReactアプリで必要になります。
-
ページ上部の スコープ タブをクリックします。 下にスクロールして、 LIFERAY.HEADLESS.ADMIN.USERをクリックし、 の代わりにデータを読み取る のチェックボックスをオンにします。

をクリックして保存します。 お客様のOAuth2アプリケーションに、管理者ユーザーAPIカテゴリに対する読み取り権限が付与されました。
-
次に、 グローバルメニュー (
) を開き、 コントロール パネル → システム設定 → セキュリティ ツール に移動します。 -
ポータルクロスオリジンリソース共有(CORS) タブに移動し、 デフォルトのポータルCORS構成をクリックします。
-
URLパターン を値
/o/headless-admin-user/*で追加します。 -
をクリックして保存します。 これにより、
headless-admin-userカテゴリの API に対して CORS が有効になります。
サンプルReactアプリをデプロイする
-
OAuth2 React アプリ をダウンロードして解凍します。
curl https://resources.learn.liferay.com/examples/liferay-c2b6.zip -Ounzip liferay-c2b6.zipcd liferay-c2b6 -
ノードとyarnがインストールされていることを確認してください。 そうでない場合は、セットアップスクリプトを実行し、画面の指示に従ってください。./setup_tutorial.sh -
アプリのルートディレクトリに移動し、Reactサーバーを起動します。
cd c2b6-custom-elementyarn install && yarn start
認証コードの流れ
認証コードフローでは、アプリに権限が付与される前に、ユーザーが認証情報を使用してログインし、認証を承認する必要があります。 他のフローでは、この追加手順は不要です。
-
http://localhost:3000で実行されている React アプリを開き、ページ上部の Authorization Code Flow をクリックします。
-
Liferay 認証 URL には、
http://localhost:8080/o/oauth2/authorizeと入力してください。 クリップボードからクライアントIDを貼り付けてください。 をクリックして承認します。 -
まだログインしていない場合は、認証ページに進む前にLiferayのログインページにリダイレクトされます。 ユーザー名とパスワードを入力し(例: test@liferay.com:learn)、 サインイン をクリックしてください。 認証ページで、 認証 をクリックします。 既にログインしている場合は、認証ページに直接移動します。

Reactアプリにリダイレクトされます。 次のAPI呼び出しに使用される認証コードが表示されますので、ご確認ください。
-
LiferayトークンURLには、
http://localhost:8080/o/oauth2/tokenを入力してください。 クリップボードからクライアントIDとクライアントシークレットを貼り付けてください。 をクリックしてトークンを取得 をクリックしてください。 今後のREST API呼び出しに使用できる認証トークンが表示されていることに注意してください。注記同じインスタンス上でトークンを要求する場合、Liferayはネットワークトラフィックを発生させません。
-
Liferay のユーザー取得 URL には、
http://localhost:8080/o/headless-admin-user/v1.0/user-accountsを入力してください。 をクリックしてデータを取得 します。 Reactアプリは、トークンベース認証を使用してLiferayに対してREST API呼び出しを行い、Liferayユーザーのリストを返します。
クライアント認証情報フロー
クライアント認証情報フローは、通常、サーバー間のやり取りに使用され、ユーザーは関与しません。
-
http://localhost:3000で実行されている React アプリを開き、ページ上部の Client Credentials Flow をクリックします。
-
LiferayトークンURLには、
http://localhost:8080/o/oauth2/tokenを入力してください。 クリップボードからクライアントIDとクライアントシークレットを貼り付けてください。 をクリックしてトークンを取得 をクリックしてください。 今後のREST API呼び出しに使用できる認証トークンが表示されていることに注意してください。 -
Liferay のユーザー取得 URL には、
http://localhost:8080/o/headless-admin-user/v1.0/user-accountsを入力してください。 をクリックしてデータを取得 します。 React アプリは、トークン・ベースの認証を使用してLiferayにREST API呼び出しを行い、Liferayユーザーのリストを返します。
パスワードフロー
パスワードフロー認証では、Reactアプリはユーザー名とパスワードをリクエストに直接含めて渡します。
パスワードフローでは、ユーザー名とパスワードがアプリケーションに直接公開されます。 したがって、ユーザーはアプリケーションを信頼する必要がある。 APIリクエストでユーザー名とパスワードを渡すことにもリスクが伴います。 パスワードフローの使用は推奨されません。
-
http://localhost:3000で実行されている React アプリを開き、ページ上部の パスワード フロー をクリックします。
-
LiferayトークンURLには、
http://localhost:8080/o/oauth2/tokenを入力してください。 -
クリップボードからクライアントIDとクライアントシークレットを貼り付けてください。
-
ユーザー名とパスワードを入力してください(例: test@liferay.com:learn)。
-
をクリックしてトークンを取得 をクリックしてください。 今後のREST API呼び出しに使用できる認証トークンが表示されていることに注意してください。
-
Liferay のユーザー取得 URL には、
http://localhost:8080/o/headless-admin-user/v1.0/user-accountsを入力してください。 をクリックしてデータを取得 します。 Reactアプリは、トークンベース認証を使用してLiferayに対してREST API呼び出しを行い、Liferayユーザーのリストを返します。
規約を検証する
React アプリの コンポーネント フォルダーは、UI 要素と、ボタンをクリックすることによって発生するイベントを処理するロジックを定義します。 例えば、 Authorize.js ファイルは認証ページにリダイレクトし、 Token.js はアクセストークンを取得し、 Users.js はユーザーのリストを取得します。 各認証フローは、これらのコンポーネントの一部または全部を使用します。
認証トークンを取得するための API リクエストと GET リクエストは、 utils ファイルで定義されています。フォルダ内の Requests.js
src
├── components
│ ├── Authorize.js
│ ├── Token.js
│ ├── Users.js
├── routes
│ ├── grant-type-authorization-code
│ | ├── AuthorizationCode.js
│ ├── grant-type-client-credentials
│ | ├── ClientCredentials.js
│ ├── grant-type-password
│ | ├── Password.js
├── utils
│ ├── Requests.js
├── App.js
└── index.js
承認付与タイプ
AuthorizationCode.js ファイル( grant-type-authorization-code フロー)は、3 つのコンポーネントすべて(Authorize.js、 Token.js、および Users.js )を使用します。
<h1>認証コードフロー</h1>
コールバック URI: http://localhost:3000/grant-type-authorization-code (または React アプリが実行されている場所)
<br />
スコープ: ヘッドレス管理者ユーザー (例: Liferay.Headless.Admin.User.everything.read)
<br />
CORS: ポータル CORS URL パターンの設定 (例: /o/headless-admin-user/*)
<Authorize />
<Token
grantType='authorization_code'
handleToken={handleToken}
/>
<Users token={token} />
コードでは、 Authorize.js コンポーネントが最初のステップを処理します。 承認 ボタンがクリックされると、承認要求が行われます。
function Authorize() {
const [authUrl, setAuthUrl] = React.useState('');
const [clientId, setClientId] = React.useState('');
function handleAuthorize(event) {
event.preventDefault();
try {
window.location.replace(
authUrl + '?response_type=code&client_id=' + clientId
);
}
catch (error) {
throw new Error(error);
}
}
const urlSearchParams = new URLSearchParams(window.location.search);
var code = urlSearchParams.get('code');
return (
<div>
<h2>Authorize</h2>
<input
onChange={(event) => setAuthUrl(event.target.value)}
placeholder="Liferay Authorize URL"
style={{width: 500}}
type="text"
value={authUrl}
/>
(例: http://localhost:8080/o/oauth2/authorize)
<br />
<input
onChange={(event) => setClientId(event.target.value)}
placeholder="クライアントID"
style={{width: 500}}
type="text"
value={clientId}
/>
<br />
<form onSubmit={handleAuthorize}>
<button type='onSubmit'>承認</button>
</form>
{コード && (
<div>
<br />
認証コード:
<br />
{code}
</div>
)}
</div>
);
}
リダイレクトとともに、ワンタイム認証コードが URL に渡されます (例: http://localhost:3000/grant-type-authorization-code?code={code})。
Token.js コンポーネントが次のステップを処理します。 トークンを取得 をクリックすると、 getAuthToken 関数が Requests.js ファイルの呼び出されます。
import {getAuthToken} from '../utils/Requests';
function Token({handleToken, grantType}) {
const [clientId, setClientId] = React.useState('');
const [clientSecret, setClientSecret] = React.useState('');
const [password, setPassword] = React.useState('');
const [token, setToken] = React.useState('');
const [tokenUrl, setTokenUrl] = React.useState('');
const [username, setUsername] = React.useState('');
async function handleGetToken() {
const token = await getAuthToken({clientId, clientSecret, grantType, password, tokenUrl, username});
handleToken(token);
setToken(token);
}
return (
<div className='Token'>
<h2>トークンの取得</h2>
<input
onChange={(event) => setTokenUrl(event.target.value)}
placeholder="Liferay トークン URL"
style={{width: 500}}
type="text"
value={tokenUrl}
/>
(例: http://localhost:8080/o/oauth2/token)
<br />
<input
onChange={(event) => setClientId(event.target.value)}
placeholder="クライアント ID"
style={{width: 500}}
type="text"
value={clientId}
/>
<br />
<input
onChange={(event) => setClientSecret(event.target.value)}
placeholder="クライアントシークレット"
style={{width: 500}}
type="text"
value={clientSecret}
/>
<br />
{grantType === 'password' && (
<div>
<input
onChange={(client) => setUsername(client.target.value)}
placeholder="ユーザー名"
style={{width: 500}}
type="text"
value={username}
/>
<br />
<input
onChange={(client) =>
setPassword(client.target.value)
}
placeholder="ユーザーパスワード"
style={{width: 500}}
type="テキスト"
value={password}
/>
<br />
</div>
)}
<button onClick={handleGetToken}>トークンの取得</button>
{token && (
<div>
<br />
認証トークン:
<br />
{token.access_token}
</div>
)}
</div>
);
}
Token.js コンポーネントでは、パラメータ client_id、 client_secret、 code、 grant_type、および redirect_uri がこの API リクエストで送信されます。 パラメータが有効な場合、Liferayはアクセストークンを含むJSONレスポンスを返します。
回答例:
{
"access_token": "2fda85abec524112dae612d35e9f9abd71650d364dee47c645b7574c6bffe91",
"token_type": "Bearer",
"expires_in": 600,
"scope": "Liferay.Headless.Admin.User.everything.read"
}
Users.js コンポーネントは、 access_token のレスポンスを解析します。
最後に、 Get Data をクリックすると、 getUsers 関数が Requests.js ファイル内で呼び出されます。
クライアント認証情報 助成金の種類
ClientCredentials.js ファイル( grant-type-client-credentials フロー)は、2 つのコンポーネント( Token.js と Users.js)を使用します。
function ClientCredentials() {
const [token, setToken] = React.useState({});
function handleToken(token) {
setToken(token);
}
return (
<div>
<h1>クライアント認証情報コードフロー</h1>
スコープ: ヘッドレス管理者ユーザー (例: Liferay.Headless.Admin.User.everything.read)
<br />
CORS: ポータル CORS URL パターンの設定 (例: /o/headless-admin-user/*)
<Token
grantType='client_credentials'
handleToken={handleToken}
/>
<Users token={token} />
</div>
);
}
Token.js コンポーネントでは、パラメータ client_id、 client_secret、および grant_type が API リクエストで送信されます。 パラメータが有効な場合、Liferayはアクセストークンを含むJSONレスポンスを返します。
Users.js コンポーネントは、 access_token のレスポンスを解析します。
最後に、 Get Data をクリックすると、 getUsers 関数が Requests.js ファイル内で呼び出されます。
パスワード付与タイプ
の ファイルは、 grant-type-password フローで 2 つのコンポーネント (つまり、 Token.js と Users.js を使用します。
function Password() {
const [token, setToken] = React.useState({});
function handleToken(token) {
setToken(token);
}
return (
<div>
<h1>パスワードフロー</h1>
スコープ: ヘッドレス管理者ユーザー (例: Liferay.Headless.Admin.User.everything.read)
<br />
CORS: ポータル CORS URL パターンの設定 (例: /o/headless-admin-user/*)
<Token
grantType='password'
handleToken={handleToken}
/>
<Users token={token} />
</div>
);
}
Token.js コンポーネントでは、パラメータ client_id、 client_secret、 grant_type、 password、および username が API リクエストのパラメータとして送信されます。 パラメータが有効な場合、Liferayサーバーはアクセストークンを含むJSONレスポンスを返します。
Users.js コンポーネントは、 access_token のレスポンスを解析します。
最後に、 Get Data をクリックすると、 getUsers 関数が Requests.js ファイル内で呼び出されます。