使用 JWT 进行身份验证时如何区分用户类型
Posted
技术标签:
【中文标题】使用 JWT 进行身份验证时如何区分用户类型【英文标题】:How to distinguish between user types when authenticating with JWT 【发布时间】:2017-12-25 08:42:39 【问题描述】:在我的应用程序(Mongo、Express、Node、React)中,我目前正在使用 JSON Web 令牌对从客户端到服务器的用户进行身份验证。但是,我希望能够让两种不同类型的用户访问应用程序的不同部分。解决此问题的最佳方法是什么?我目前将两种类型的用户保存在同一个模型中,并使用一个布尔值来区分它们。澄清一下,不同类型的用户将能够访问不同的 API 以及客户端应用程序的不同部分。
有处理这个的包吗? JWT 功能?
【问题讨论】:
好问题。想知道同样的事情只是为了区分移动用户和网络用户。 【参考方案1】:有两种方法可以做到这一点:
-
在对 JWT 令牌进行编码时,还要对用户角色进行编码。
例如,当您解码 JWT 令牌并获取用户 ID 时,查询您的数据存储以获取该用户的角色。
大多数包都允许您定义要编码的内容。
提示:
始终为您的令牌设置到期时间。它只是一个存储在的日期 智威汤逊。当您解码令牌时,只需确保日期是 将来,如果不拒绝访问。
创建一个检查用户角色的中间件。例如:
router.get('/restricted-area', requiresAdmin, (req, res, next) =>
// only admin can access this
);
function requiresAdmin(req, res, next)
if(req.user.admin !== true)
res.status(401).end();
else
next();
【讨论】:
很好的调用 - 在服务器端应该很容易使用。在 React 中处理令牌的任何提示? React 端不需要处理。只需将令牌存储在本地存储或您喜欢的任何地方。并且可能定义一个请求拦截器,每次您制作一个时都会将令牌添加到请求标头中。当用户注销时,只需清除令牌即可。 那么我将如何确定允许用户访问 react 应用程序中的哪些页面?理想情况下,我可以根据用户类型来区分这一点。如果这不可能,有没有一种传统的方法来做我所说的? 我不是 React 用户,但应该有一个hook
供您检查。例如,VueJs 中的 beforeCreated
钩子允许您在创建模块之前执行任务。【参考方案2】:
想在建议的答案中添加一些内容。我从 Auth0 如何使用 jwt 中得到了很多。您可能想尝试一下,看看他们如何处理身份验证和保护他们的路线。另一件真正帮助我理解使用 jwt 的方法是在jwt website 上使用调试器。
允许用户访问不同的 API 端点
任何人都可以使用 jwt 令牌decoded。任何人都可以看到令牌上的内容。 jwt 的重要部分是它有一个签名。如果有人想要获取令牌,更改信息然后访问您的 api,那么 签名 将被搞砸,该令牌应该被拒绝。
您需要做的就是创建一个路由中间件。如果路由受到保护,则用户在标头中发送 jwt。中间件会做两件事:
检查令牌的签名,确保令牌有效且未被篡改。
解码令牌以查看 JSON 上的内容。由于 jwt 只是一个 JSON,因此您可以向其添加任何您想要的属性。添加属性权限并设置用户权限的级别。这是来自 auth0 的教程,介绍了 slack 等现实生活中的公司如何使用 jwt 令牌来定义用户可以做什么和不可以做什么。许多相同的原则适用于您想要做的事情。 Auth0 with multi tenant apps
如何使用 React 限制用户客户端?
我在 cmets 中看到了这个问题,如果有人感兴趣,我会在这里给出答案。如果有人真的想要,他们可以拿走他们的令牌,改变它,然后进入任何视觉组件(在反应中)。出现这种情况的原因是您不想在客户端上保留任何令牌签名机密。但就算有人换了他们的令牌,也不会造成任何伤害。如果他们尝试向服务器发送请求,他们的令牌将被拒绝,您的 api 将受到保护。
React 路由器和动态路由
对于 99.9% 的用户不会弄乱他们的令牌,决定允许他们使用网站哪些部分的最佳方法是使用 react-router。由于 React 是一个单页应用程序,因此只有一个静态 html 文件会将您的构建发送到客户端。对于其他框架,服务器上的不同路由将在不同的静态端点发送不同的页面。为了用 React 模拟这种页面行为,人们使用 React Router 是很常见的。 React Router 创建动态路由,因此当用户将端点插入浏览器时,它可以模仿典型静态站点的工作方式。
它也可以用来限制用户访问某些组件。用户登录后,您可以发送解码后的令牌信息并将其保存到您的反应状态。其中之一是您的权限参数。使用反应路由器,当用户尝试导航到需要权限的位置时,您可以引用他们的状态并将它们重定向到受保护的组件或返回到授权的捕获,返回到它们来自的位置,登录页面等。基本上哪里都行。
Here is a, slightly confusing implementation on the react router documentation site about implementing restricted endpoints.
Another tutorial from auth0 using react router to restrict users。滚动到标题处理身份验证结果
【讨论】:
:D没问题!我花了一点时间才把头绕在 jwt 上。 Auth0 在 github 上有很多东西可以在解码或检查签名时很有帮助。 github.com/auth0以上是关于使用 JWT 进行身份验证时如何区分用户类型的主要内容,如果未能解决你的问题,请参考以下文章
在 Spring Boot 中使用 JWT 进行简单的身份验证
如何使用 JWT 在 Express 中验证单个路由(无代码重复)的多种类型用户的身份验证令牌?