paint-brush
如何使用 Ruby on Rails 实现一键式 Google 登录经过@shlokashah
7,874 讀數
7,874 讀數

如何使用 Ruby on Rails 实现一键式 Google 登录

经过 Shloka Shah6m2022/09/25
Read on Terminal Reader
Read this story w/o Javascript

太長; 讀書

Google 身份服务提供了一个自定义的登录/注册按钮。我们将讨论如何在使用 Ruby on Ruby on Rails 作为服务器的前端应用程序中使用 Google Sign In 或 One Tap。我们需要在 Google Developer Console 中创建一个应用程序来使用 OAuth 客户端 ID。我们还需要设置我们的一键登录按钮,以显示 Google 已在我们的应用程序中全局定义。我们还可以使用 One Tap Button 来显示自定义的登录按钮。

Company Mentioned

Mention Thumbnail
featured image - 如何使用 Ruby on Rails 实现一键式 Google 登录
Shloka Shah HackerNoon profile picture

使用Google 登录进行身份验证是现代应用程序中的常见做法。在这篇博文中,我们将讨论如何将 Google 身份服务集成到任何使用Ruby on Rails作为服务器的前端应用程序中。 Google 身份服务提供


  1. 自定义登录/注册按钮

一键登录

让我们潜入!


第 1 步:在 Google Developer Console 中创建一个应用程序。

为了使用 Google Sign In 或 One Tap,我们需要一个client_id来添加我们的client以及server


  • 要创建应用程序,请前往谷歌开发者控制台

  • 选择Create Credentials > OAuth Client ID 。在执行此操作之前,您需要配置您的同意屏幕.

  • 创建 client_id 时,请确保在 Authorized Javascript Origin for development 和生产 URL 中包含localhost和客户端运行的端口。


  • 完成后,您将获得格式为1234567890-abcdefg.apps.googleusercontent.comclient_id


有关设置应用程序的更多详细信息,您可以阅读在这里

第 2 步:在客户端中设置库

为了加载客户端库,如果您使用React.js或 _app,请在index.html中添加<script src="https://accounts.google.com/gsi/client" async defer></script> _app.jsx如果使用Next.js。

第 3 步:显示自定义的登录按钮

 useEffect(() => { /* global google */ google.accounts.id.initialize({ client_id: "YOUR_GOOGLE_CLIENT_ID", callback: signInCallback, cancel_on_tap_outside: false, }); google.accounts.id.renderButton(document.getElementById("signInDiv"), { theme: "outline", size: "large", }); }, []);


  • 添加global google以显示 google 已在我们的index.html中全局定义


  • google.accounts.id.initialize方法基于给定字段创建一个 Sign In With Google 客户端实例。 client_id是我们从创建 google 应用程序中获得的必填字段,回调是 JavaScript 函数(此处为 signInCallback ),用于处理从 One Tap 提示或弹出窗口返回的 ID 令牌。


  • 默认情况下,如果用户单击屏幕上的任意位置,则会在 One Tap 提示上应用指数冷却。如果您希望提示始终可见,请将此值设置为false 。您可以查看更多配置这里。


  • google.accounts.id.renderButton方法呈现一个 Sign In With Google 按钮。你可以玩弄配置这里。


  • document.getElementById("signInDiv")是 HTML 元素。通过将以下代码添加到您的网页 HTML,

 return ( <div className="App"> <div id="signInDiv" /> </div> );


您将能够看到这样的自定义按钮

第 4 步:显示一键式提示

  • 为了显示提示,将其添加到 useEffect google.accounts.id.prompt();

第 5 步:定义回调函数

  • 第 3 步所述,signInCallback 是我们的回调函数,可以定义为
const signInCallback = (result) => { if (result.credential) { const params = { token: result.credential }; axios .post("http://localhost:3000/user/google", params) .then((res) => { const { authToken, ...userInfo } = res.data.data; // set token in local storage/cookies based on your authentication method // redirect to the authenticated page }) .catch((err) => console.log(err)); } };


在哪里,

  • 本地主机:3000/用户/谷歌是我们将在下一步中创建的服务器 URL


  • 一旦我们单击“登录”或“一键式”按钮,结果就是来自 Google 的响应。


  • 结果包含两个字段

    • credential :此字段是作为 base64 编码的 JSON Web 令牌 (JWT) 字符串的 ID 令牌

    • select_by :显示如何选择凭证。更多关于它这里.


  • 我们从结果中获取凭证并将其作为参数传递给我们的服务器。

第 6 步:将控制器和路由添加到服务器

我们将在服务器中创建一个路由来处理来自客户端的请求。在我们这样做之前,我们需要创建一个控制器来接受来自客户端的 JWT。


  • 创建一个文件app/controllers/users/user_controller.rb ,添加一个方法google


  • config/routes.rb中添加路由users/user# google_oauth 。


  • 一旦路由收到 JWT,第一步也是最关键的一步是验证 JWT 是否经过验证。为此,我们可以使用 gem google_auth ,这是来自 Google 的官方 gem,用于验证颁发的 ID 令牌。


  • 这可以很容易地使用

Google::Auth::IDTokens.verify_oidc access_token, aud: "YOUR_GOOGLE_CLIENT_ID"

其中access_token是从客户端收到的 JWT,而aud是谷歌应用程序客户端 ID。


  • 如果令牌有效,它将返回这样的哈希或抛出异常
{ "iss": "https://accounts.google.com", "nbf": 12345678, "aud": "YOUR_GOOGLE_CLIENT_ID, "sub": "1112223333444", "email": "[email protected]", "email_verified": true, "azp": "YOUR_GOOGLE_CLIENT_ID", "name": "First Last", "picture": "https://lh3.googleusercontent.com/a/AItbvmnvsIQFJw", "given_name": "First", "family_name": "Last", "iat": 1653797115, "exp": 1653805725, "jti": "8ffa19190gngd46745ff558821f953802" }


  • 如果令牌有效,您可以在数据库中检查用户是否存在并相应地创建用户。完成后,您可以根据您的身份验证方法登录或重定向用户。


 # users/user_controller.rb def google begin data = Google::Auth::IDTokens.verify_oidc access_token, aud: "YOUR_GOOGLE_CLIENT_ID" // find the user in the data // if the user does not exist, create a user using data // sign the user (based on your authentication method) rescue StandardError => e end end


 # config/routes.rb scope :user do post 'google' => 'users#user_controller.rb' end


PS :确保在您的服务器上安装rack-cors并添加此application.rb


 config.middleware.insert_before 0, Rack::Cors do allow do origins '*' resource( '*', headers: :any, expose: ['Authorization'], methods: %i[get patch put delete post options show] ) end end


避免遇到这样的错误

PPS :如果您的应用程序使用适用于 Web 的 Google 登录 JavaScript 平台库,请确保将其迁移到 Google 身份服务,因为前者将被弃用。关联


我希望本文能帮助您将 One Tap Login 集成到您的项目中。更详细的信息可以查看官方文档.


也在这里发布