【问题标题】:How do I get the result from a Promise?如何从 Promise 中获得结果?
【发布时间】:2021-01-13 23:12:59
【问题描述】:

我有一个向我的后端发送 post 请求的函数,它包含 JWT 令牌,然后后端检查这个令牌是否正确。不幸的是,isAuthenticated() 函数仅在我返回 Promise 时才有效。但是我现在想在我的 ProtectedRoute.tsx 中检查令牌是否正确。这如何与 Promise 一起使用?

isAuthenticated():

import axios from "axios"

let token = localStorage.getItem("jwt-token");

export const isAuthenticated = async (): Promise<boolean> => {
    if (!token) {
        return false;
    } else {
        let tokenCheck = false;
        await axios.post("/api/users/tokencheck", { token: token }).then((res) => {
            if (res.data === "Valid Token" || res.status === 200) {
                tokenCheck = true
            } else {
                tokenCheck = false
            }
        })
        return tokenCheck
    }
}

ProtectedRoute.tsx:

import React from 'react'
import { Redirect, Route } from 'react-router-dom'
import { isAuthenticated } from "./Auth"

interface Props {
    component: React.FC;
    path: string;
}

const ProtectedRoute: React.FC<Props> = (props: Props) => {
    return (
        <React.Fragment>
            {isAuthenticated()
                ? <Route path={props.path} exact component={props.component} />
                : <Redirect to="/" />
            }
        </React.Fragment>
    )
}

export default ProtectedRoute

后端:

export const tokenCheck = (req: Request, res: Response) => {
    let { token } = req.body
    jwt.verify(token!, process.env.JWTSECRET!, (err: any, decoded: any) => {
        if (err) {
            res.status(401).json("Invalid token");
        } else {
            res.status(200).json("Valid Token")
        }
    })
}

【问题讨论】:

  • 考虑返回then中的值,然后返回await axios.post的输出?
  • store isAuthenticated 到 redux 或者使用 Context, ProtectedRoute 观察结果
  • isAuthenticated() 被声明为返回一个 Promise,但它不返回一个 Promise:它返回 true 或 false。

标签: javascript reactjs typescript promise jwt


【解决方案1】:

在 TokenContext 中存储 isAuthenticated,

import React from 'react';

const TokenContext = React.createContext<{
  token: string;
  saveToken: (token: string) => void;
  isAuthenticated: boolean;
}>(null as never);
const TokenProvider: React.FC = ({ children }) => {
  const [token, setToken] = React.useState(
    () => localStorage.getItem('jwt-token') || ''
  );
  const [isAuthenticated, setIsAuthenticated] = React.useState(false);
  const [loading, setLoading] = React.useState(false);
  const [error, setError] = React.useState<string | null>(null);
  React.useEffect(() => {
    if (!token || isAuthenticated) {
      return;
    }
    setLoading(true);
    axios.post(...).then(
      (res) => {
        setIsAuthenticated(res.ok);
        setLoading(false);
      },
      (err: Error) => {
        setLoading(false);
        setError(err.message)
      }
    );
  }, [token, isAuthenticated]);
  const saveToken = React.useCallback((v: string) => {
    localStorage.setItem('jwt-token', v);
    setToken(v);
    setIsAuthenticated(true);
  }, []);
  if (loading) {
    return <>Authorizing....</>;
  }
  if (error){
    return <>{error}</>
  }
  return (
    <TokenContext.Provider value={{ token, isAuthenticated, saveToken }}>
      {children}
    </TokenContext.Provider>
  );
};

interface Props {
  component: React.FC;
  path: string;
}

const ProtectedRoute: React.FC<Props> = (props: Props) => {
  const { isAuthenticated } = React.useContext(TokenContext);
  return (
    <>
      {isAuthenticated
        ? <Route path={props.path} exact component={props.component} />
        : <Redirect to="/" />
      }
    </>
  )
}

const App: React.FC = ()=> {
  <TokenProvider>
      <div className="App">
        <Router>
          <Switch>
            <Route exact path="/" component={Login} />
            <ProtectedRoute path="/dashboard" component={Dashboard} />
            <Route component={NoMatch} />
          </Switch>
        </Router>
      </div>
    </TokenProvider>
}

【讨论】:

  • 它有效,但我有第二条登录路由,现在从登录到 ProtectedRoute => {isAuthenticated ? /dashboard 是 ProtectedRoute
猜你喜欢
  • 2014-03-10
  • 2019-03-27
  • 2021-12-28
  • 2020-10-05
  • 2014-08-30
  • 2020-03-03
  • 2013-04-12
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多