当前位置: 首页 > 科技观察

通过Vue使用RESTfulAPI处理认证

时间:2023-03-22 01:43:01 科技观察

本文转载自微信公众号《新钛云服务》,作者李冰。转载本文请联系新钛云服务公众号。身份验证(登录!)是许多网站的重要组成部分。让我们看看如何使用Vue在网站上执行此操作,就像我们在任何自定义后端中执行此操作一样。Vue本身并不能真正完成身份验证,我们需要另一种服务,因此我们将为此使用另一种服务(Firebase),然后将整个体验集成到Vue中。身份验证在单页应用程序(SPA)上的工作方式与在重新加载每个页面的站点上完全不同。我们将构建一个用户登录界面,并将提交的数据发送到服务器以检查用户是否存在。如果是,我们将收到令牌。这非常有用,因为它将在我们的整个站点中使用,以检查用户是否仍处于登录状态。如果没有,用户可以随时注册。换句话说,它可以在许多条件上下文中使用。除此之外,如果我们需要来自服务器的任何需要登录的信息,令牌将通过URL发送到服务器,这样信息将只发送给登录用户。本教程的完整演示发布在GitHub上,供熟悉阅读代码的人使用。我们其他人可以继续阅读这篇文章。起始文件也在GitHub上,因此您可以在我们一起编码的同时继续工作。下载后,在终端运行npminstall。如果你想完全自己构建这个应用程序,你必须安装Vuex、VueRouter和axios。我们还将在此项目中使用Firebase,因此请花点时间设置一个免费帐户并在其中创建一个新项目。将项目添加到Firebase后,转到身份验证部分,并设置登录方法,这将使用传统的电子邮件/密码提供程序,它将存储在Firebase服务器上。之后,我们将转到FirebaseAuthRESTAPI文档以获取我们的注册和登录API端点。我们需要一个API密钥才能在我们的应用程序中使用这些端点,它可以在Firebase项目设置中找到。Firebase通过SDK提供身份验证,但我们使用AuthAPI来演示通过任何自定义后端服务器进行的身份验证。在我们的状态报告文件中,下面有一张注册表。由于我们专注于学习概念,因此我们在这里保持简单。如果我们不't使用SPA,我们很自然地使用axios将数据发送到脚本标签中,就像这样:axios.post('https://identitytoolkit.googleapis.com/v1/accounts:signUp?key=[API_KEY]',{email:authData.email,password:authData.password,returnSecureToken:true}).then(res=>{console.log(res)}).catch(error=>console.log(error))}}注册并登录使用SPA(在本例中为Vue)与上述方法有很大不同。相反,我们将在文件store.js中的操作中使用Vuex来发送授权请求。我们这样做是因为我们希望整个应用程序都知道用户身份验证状态的任何更改。actions:{signup({commit},authData){axios.post('https://identitytoolkit.googleapis.com/v1/accounts:signUp?key=[API_KEY]',{email:authData.email,password:authData.password,returnSecureToken:true}).then(res=>{console.log(res)router.push("/dashboard")}).catch(error=>console.log(error))},login({commit},authData){axios.post(https://identitytoolkit.googleapis.com/v1/accounts:signIn?key=[API_KEY]',{email:authData.email,password:authData.password,returnSecureToken:true}).then(res=>{console.log(res)router.push("/dashboard")}).catch(error=>console.log(error))}}我们可以使用几乎相同的登录方式方法,但可以改用登录API端点。然后,我们将组件的注册和登录分派到它们在商店中的相应操作。方法:{onSubmit(){constformData={email:this.email,name:this.name,password:this.password}this.$store.dispatch('signup',formData)}}}formData包含用户的数据。方法:{onSubmit(){constformData={email:this.email,password:this.password}this.$store.dispatch('login',{email:formData.email,password:formData.password})}}我们从注册/登录表单收到的身份验证数据(即令牌和用户ID)将被用作Vuex的状态。初始结果为空。state:{idToken:null,userId:null,user:null}现在我们在mutation中创建一个名为authUser的新方法,它将存储从响应中收集的数据。我们需要将路由器导入商店,因为我们稍后会需要它。importrouterfrom'/router'mutations:{authUser(state,userData){state.idToken=userData.tokenstate.userId=userData.userId}}.then在我们操作的注册/登录方法的块内,我们将调用authUser的响应刚刚创建的突变被提交并保存到本地存储。actions:{signup({commit},authData){axios.post('https://identitytoolkit.googleapis.com/v1/accounts:signUp?key=[API_KEY]'),{email:authData.email,password:authData.password,returnSecureToken:true}).then(res=>{console.log(res)commit('authUser',{token:res.data.idToken,userId:res.data.localId})localStorage.setItem('token',res.data.idToken)localStorage.setItem('userId',res.data.localId)router.push("/dashboard")}).catch(error=>console.log(error))},login({commit},authData){axios.post('https://identitytoolkit.googleapis.com/v1/accounts:signIn?key=[API_KEY]'),{email:authData.email,password:authData.password,returnSecureToken:true}).then(res=>{console.log(res)commit('authUser',{token:res.data.idToken,userId:res.data.localId})localStorage.setItem('token',res.data.idToken)localStorage.setItem('userId',res.data.localId)router.push("/dashboard")}).catch(error=>console.log(error))}}setauthenticationGuard现在我们已经将令牌存储在应用程序中,我们将在设置时使用此令牌注册AuthGuard。什么是AuthGuard?它保护仪表板,防止未经身份验证的用户在没有令牌的情况下访问仪表板。首先,我们将进入我们的路由文件并导入商店。导入商店是因为令牌将确定用户的登录状态。importstorefrom'./store.js'因此,在我们的路由数组中,转到仪表板路由,添加方法beforeEnter此方法具有三个参数:to、from和next。在此方法中,如果令牌已存储,我们只需说下一步(如果已通过身份验证,这将自动完成),这意味着令牌将沿着指定的路线继续。否则,我们将未经身份验证的用户带回注册页面。{path:'/dashboard',component:DashboardPage,beforeEnter(to,from,next){if(store.state.idToken){next()}else{next('/signin')}}}创建UI状态,无论是否登录,我们仍然可以在导航中看到仪表盘,这不是我们想要的。我们必须在名为ifAuthenticated的getter下添加另一个方法,检查状态中的令牌是否为空,然后相应地更新导航项。getters:{user(state){returnstate.user},ifAuthenticated(state){returnstate.idToken!==null}}接下来,让我们打开头组件并在计算属性中创建一个名为auth的方法。这将发送给我们刚刚在商店中创建的ifAuthenticatedgetter。如果没有令牌,ifAuthenticated将返回false,这自动意味着auth也将为null,反之亦然。在此之后,我们添加一个v-if检查,如果auth是否为空,以确定仪表板选项是否将显示在导航中。注销什么是没有注销按钮的应用程序?让我们创建一个名为clearAuth的新突变,它将token和userId都设置为null。mutations:{authUser(state,userData){state.idToken=userData.tokenstate.userId=userData.userId},clearAuth(state){state.idToken=nullstate.userId=null}}然后,在我们的注销操作中,我们提交要clearAuth,删除本地存储并添加router.replace('/')以在注销后正确重定向用户。返回标头组件。我们有一个onLogout方法,用于logout调度我们在商店中的操作。然后我们向按钮添加一个@click,它将像这样调用onLogout方法:自动登录?当然!我们的申请快完成??了。我们可以使用刚刚所做的所有UI更改来注册、登录和注销。但是,当我们刷新应用程序时,我们会丢失数据并注销并且必须重新开始,因为我们将令牌和ID存储在JavaScript的Vuex中。这意味着刷新后,应用程序中的所有内容都会重新加载到浏览器中。我们要做的是在本地存储中检索令牌。这样,无论何时刷新窗口,我们都可以在浏览器中获得用户的令牌,甚至可以在令牌仍然有效的情况下自动登录用户。创建一个名为userId的新操作方法,只有当用户拥有AutoLogin令牌时,我们才能从本地存储中获取令牌。然后我们将数据提交给突变中的authUser方法。操作:{AutoLogin({commit}){consttoken=localStorage.getItem('token')if(!token){return}constuserId=localStorage.getItem('userId')consttoken=localStorage.getItem('token')commit('authUser',{idToken:token,userId:userId})}然后我们转到App.vue的创建方法,并在autoLogin加载应用程序时从商店分派。created(){this.$store.dispatch('AutoLogin')}太棒了!有了这个,我们已经成功地在应用程序中进行了身份验证,现在可以使用npmrunbuild进行部署。观看现场演示以查看实际效果。原文:https://css-tricks.com/tackling-authentication-with-vue-using-restful-apis/