使用Google 登录进行身份验证是现代应用程序中的常见做法。在这篇博文中,我们将讨论如何将 Google 身份服务集成到任何使用Ruby on Rails作为服务器的前端应用程序中。 Google 身份服务提供
自定义登录/注册按钮
一键登录
让我们潜入!
为了使用 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.com
的client_id
有关设置应用程序的更多详细信息,您可以阅读
为了加载客户端库,如果您使用React.js或 _app,请在index.html
中添加<script src="https://accounts.google.com/gsi/client" async defer></script>
_app.jsx
如果使用Next.js。
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> );
您将能够看到这样的自定义按钮
google.accounts.id.prompt();
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)); } };
在哪里,
一旦我们单击“登录”或“一键式”按钮,结果就是来自 Google 的响应。
结果包含两个字段
credential :此字段是作为 base64 编码的 JSON Web 令牌 (JWT) 字符串的 ID 令牌
select_by :显示如何选择凭证。更多关于它
我们从结果中获取凭证并将其作为参数传递给我们的服务器。
我们将在服务器中创建一个路由来处理来自客户端的请求。在我们这样做之前,我们需要创建一个控制器来接受来自客户端的 JWT。
创建一个文件app/controllers/users/user_controller.rb
,添加一个方法google
。
在config/routes.rb中添加路由users/user# google_oauth 。
一旦路由收到 JWT,第一步也是最关键的一步是验证 JWT 是否经过验证。为此,我们可以使用 gem
这可以很容易地使用
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 集成到您的项目中。更详细的信息可以查看官方
也在这里发布