makabe.t 0212c61bbc Merged PR 550: 画面実装(トークンを定期的に更新する仕組み)
## 概要
[Task2910: 画面実装(トークンを定期的に更新する仕組み)](https://paruru.nds-tyo.co.jp:8443/tfs/ReciproCollection/fa4924a4-d079-4fab-9fb5-a9a11eb205f0/_workitems/edit/2910)

- タイマーで定期的に代行操作用のアクセストークンを更新する処理を実装しました。

## レビューポイント
- 通常のアクセストークンのタイマー内で同じタイミングでチェックするように実装していますが分けたほうがいいなどありますでしょうか?

## UIの変更
- [Task2910](https://ndstokyo.sharepoint.com/:f:/r/sites/Piranha/Shared%20Documents/General/OMDS/%E3%82%B9%E3%82%AF%E3%83%AA%E3%83%BC%E3%83%B3%E3%82%B7%E3%83%A7%E3%83%83%E3%83%88/Task2910?csf=1&web=1&e=g0RdIf)

## 動作確認状況
- ローカルで確認
2023-11-07 07:15:25 +00:00

61 lines
2.0 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import React, { useCallback } from "react";
import { AppDispatch } from "app/store";
import { decodeToken } from "common/decodeToken";
import { useInterval } from "common/useInterval";
import {
updateTokenAsync,
loadAccessToken,
updateDelegationTokenAsync,
} from "features/auth";
import { DateTime } from "luxon";
import { useDispatch, useSelector } from "react-redux";
import { selectDelegationAccessToken } from "features/auth/selectors";
import { useNavigate } from "react-router-dom";
import { cleanupDelegateAccount } from "features/partner";
import { TOKEN_UPDATE_INTERVAL_MS, TOKEN_UPDATE_TIME } from "./constants";
export const UpdateTokenTimer = () => {
const dispatch: AppDispatch = useDispatch();
const navigate = useNavigate();
const delegattionToken = useSelector(selectDelegationAccessToken);
// 期限が分以内であれば更新APIを呼ぶ
const updateToken = useCallback(async () => {
// localStorageからトークンを取得
const jwt = loadAccessToken();
// 現在時刻を取得
const now = DateTime.local().toSeconds();
// selectorに以下の判定処理を移したかったが、初期表示時の値でしか判定できないのでComponent内に置く
if (jwt) {
const token = decodeToken(jwt);
if (token) {
const { exp } = token;
if (exp - now <= TOKEN_UPDATE_TIME) {
await dispatch(updateTokenAsync());
}
}
}
// 代行操作トークン更新処理
if (delegattionToken) {
const token = decodeToken(delegattionToken);
if (token) {
const { exp } = token;
if (exp - now <= TOKEN_UPDATE_TIME) {
const { meta } = await dispatch(updateDelegationTokenAsync());
if (meta.requestStatus === "rejected") {
dispatch(cleanupDelegateAccount());
navigate("/partners");
}
}
}
}
}, [dispatch, delegattionToken, navigate]);
useInterval(updateToken, TOKEN_UPDATE_INTERVAL_MS);
// eslint-disable-next-line react/jsx-no-useless-fragment
return <></>;
};