nextとredux-observableを使用して、 react server-side-rendering を実装しようとしていましたが、今は auth を実装したいと思います
サインイン時
- ログインをクリック
- ディスパッチサインイン
- ログインタイプを設定する
- サインイン データの設定
- バックエンド API の認証/サインインを呼び出す
- 応答がトークンの有効期限が切れていることを示している場合
- refreshToken を使用してコール バック API auth/refresh
- 認証/更新応答トークンに基づいて Cookie を設定する
- 認証/更新応答に基づいて認証データを設定する
- そうしないと
- 認証/サインイン応答トークンに基づいて Cookie を設定する
- 認証/サインイン応答に基づいて認証データを設定する
- 応答がトークンの有効期限が切れていることを示している場合
- ディスパッチサインイン
認証が必要なページへのアクセスについて
- 呼び出された Cookie を確認します
token
- 存在する場合
- 認可するためのコール バック API auth/me
- 応答がトークンの有効期限が切れていることを示している場合
- refreshToken を使用してコール バック API auth/refresh
- 認証/更新応答トークンに基づいて Cookie を設定する
- auth/refresh に基づいて認証データを設定する
- そうしないと
- auth/me レスポンスに基づいて認証データを設定する
- そうしないと
- サインインにリダイレクト
- 存在する場合
上記の手順は、次のようにエピック内で行われます
/epics/signin.js
export const signinEpic = (action$, store) => action$
.ofType(SIGNIN)
.mergeMap(() => {
const params = { ... }
return ajax(params)
.concatMap((response) => {
const { name, refreshToken } = response.body
if (refreshToken && name === 'TokenExpiredError') {
const refreshParams = { ... }
return ajax(refreshParams)
.concatMap((refreshResponse) => {
setToken(refreshResponse.body.auth.token)
const me = { ... }
return [
authSetMe(me),
signinSuccess(),
]
})
.catch(error => of(signinFailure(error)))
}
const me = { ... }
setToken(response.body.auth.token)
return [
authSetMe(me),
signinSuccess(),
]
})
.catch(error => of(signinFailure(error)))
})
Cookieが保存されるようにするためにいくつかのconsole.log(Cookies.get('token'))
ことを行い、そこにあると言ってトークンを正常に出力しましたが、ブラウザーコンソール>アプリケーション> Cookiesで確認したところ、何もありません
したがって、以下の auth epic では、getToken()
は常に返さ''
れ、常にディスパッチされますauthMeFailure(error)
/epics/auth.js
// this epic will run on pages that requires auth by dispatching `authMe()`
export const authMeEpic = action$ => action$
.ofType(AUTH_ME)
.mergeMap(() => {
const params = {
...,
data: {
...
Authorization: getToken() ? getToken() : '', // this will always return ''
},
}
return ajax(params)
.mergeMap((response) => {
const { name, refreshToken } = response.body
if (refreshToken && name === 'TokenExpiredError') {
const refreshParams = { ... }
return ajax(refreshParams)
.mergeMap((refreshResponse) => {
setToken(refreshResponse.body.auth.token)
const me = { ... }
return authMeSuccess(me)
})
.catch(error => of(authMeFailure(error)))
}
const me = { ... }
setToken(response.body.auth.token)
return authMeSuccess(me)
})
.catch(error => of(authMeFailure(error)))
})
Cookieの取得と設定にjs-cookieを使用します
編集:次のように、getToken、setToken、removeToken を含む認証ライブラリを実際に準備しました。
import Cookies from 'js-cookie'
export const isAuthenticated = () => {
const token = Cookies.get('token')
return !!token
}
export const getToken = () => Cookies.get('token')
export const setToken = token => Cookies.set('token', token)
export const removeToken = () => Cookies.remove('token')
はい、setToken()
エピックで を使用することもできましたが、Cookie セット メソッドを直接テストしようとしていました。
アップデート:
- コンソール>アプリケーション> Cookiesにないにもかかわらず
console.log(getToken())
、コンポーネントのレンダリングメソッド内で行うと正しいトークンを出力しているため、すべてのページに存在するようです - しかし、ページを更新するたびに消えてしまいます。変な還元状態で保存されているようなものです
更新#2:
わかりました私はそれを機能させることができたと思います.2種類のCookie、サーバー側(更新時に生成されるもの)とクライアント側(ナビゲートを持続する)が必要であることが判明したので、私ができなかった理由サーバー側から渡されなかったため、エピックでトークンを取得します(少なくともこれは私の理解です)