Ory Kratos 用户认证

article/2025/10/5 12:21:45

Ory Kratos 为用户认证与管理系统。本文将动手实现浏览器(React+AntD)的完整流程,实际了解下它的 API 。

  • 代码: https://github.com/ikuokuo/start-ory-kratos

了解 Kratos

获取代码

git clone -b v0.7.0-alpha.1 --depth 1 https://github.com/ory/kratos.git

查看 API

go-swagger 查看:

cd kratos
swagger serve -F=swagger ./spec/swagger.json

运行服务

docker-compose 运行:

cd kratos
docker-compose -f quickstart.yml -f quickstart-postgres.yml -f quickstart-standalone.yml up --build --force-recreate
# If you have SELinux, run: -f quickstart-selinux.yml

运行了官方 Quickstart 例子,可以访问 http://127.0.0.1:4455/dashboard 体验。

查看 DB

pgAdmin 打开(DB 信息见 quickstart-postgres.yml):

查看表:

查看配置

cd kratos
cat contrib/quickstart/kratos/email-password/kratos.yml

设置环境变量可以覆盖。以 _ 表示层级,如 SELFSERVICE_FLOWS_SETTINGS_UI_URL=<value> 覆盖 selfservice.flows.settings.ui_url

Self-Service 流程

  • Registration
  • Login
  • Logout
  • User Settings
  • Account Recovery
  • Address Verification
  • User-Facing Error
  • 2FA / MFA

浏览器流程

客户端流程

动手配置:Kratos 服务

  • Ory Kratos
    • Public API (port 4433)
    • Admin API (port 4434)
    • Postgres DB (port 5432)
    • Browser Return URL (port 3000)
  • MailSlurper: a development SMTP server
    • Server UI (port 4436)

配置文件

  • ory-kratos/config/kratos.yml: 配置文件
  • ory-kratos/config/identity.schema.json: 认证 JSON 模式

启动文件

  • ory-kratos/start.yml: Docker Compose 文件

运行服务

cd ory-kratos
docker-compose -f start.yml up --build --force-recreate

如果想运行官方 Self-Service UI 例子,那么:

docker-compose -f start.yml -f start-ui-node.yml up --build --force-recreate

之后,访问 http://127.0.0.1:3000/ 体验。在 Register new account / Reset password 时,可访问虚拟 SMTP 服务 http://127.0.0.1:4436 接收邮件。

动手实现:浏览器流程

React + Ant Design

新建 React 应用

yarn create react-app my-web --template typescript
cd my-web
yarn start

访问 http://localhost:3000/ ,可见 React 欢迎页。

引入 AntD

yarn add antd

修改 src/App.tsx,引入 antd 组件:

import React, { Component } from 'react'
import { Button } from 'antd';
import logo from './logo.svg';
import './App.css';class App extends Component {render() {return (<div className="App"><header className="App-header"><img src={logo} className="App-logo" alt="logo" /><Button type="primary">Button</Button></header></div>);}
}export default App;

修改 src/App.css,引入 antd 样式:

@import '~antd/dist/antd.css';

可见 antd 蓝色按钮组件。

引入 Sass

yarn add node-sass

后缀 css 改为 scsstsx 里的 import 也改下。

引入 Router

yarn add react-router-dom @types/react-router-dom

pages 目录下实现如下页面 UI:

src/pages               功能        路由
├── dashboard.tsx       主页        /, /dashboard
├── error.tsx           错误        /error
├── login.tsx           登录        /auth/login
├── recovery.tsx        恢复        /recovery
├── registration.tsx    注册        /auth/registration
├── settings.tsx        设置        /settings
└── verification.tsx    验证        /verify

引入 SDK

yarn add @ory/kratos-client@0.7.0-alpha.1

注册

APIs:

  • GET /self-service/registration/browser: 初始化注册流程
  • GET /self-service/registration/flows: 获取注册流程
  • POST /self-service/registration: 提交注册流程

页面加载后的处理流程:

componentDidMount() {// 获取 flow id 参数const flowId = utils.parseUrlQuery("flow", this.props.location) as string;// 没有 flow id,初始化注册流程if (!flowId || !utils.isString(flowId)) {console.log("No flow ID found in URL, initializing registration flow.");utils.redirectToSelfService("/self-service/registration/browser");return;}// 根据 flow id,获取注册流程信息authPublicApi.getSelfServiceRegistrationFlow(flowId, undefined, {withCredentials: true,}).then((res: AxiosResponse<SelfServiceRegistrationFlow>) => {if (utils.assertResponse(res)) {utils.redirectToSelfService("/self-service/registration/browser");return;}this.setState({ flowId: flowId, flow: res.data });}).catch(utils.redirectOnError);
}

流程信息 this.state.flow,如下:

{"id": "74c643a1-f302-45c9-a760-1ad7b1157e1c","type": "browser","expires_at": "2021-07-20T05:22:30.958717Z","issued_at": "2021-07-20T05:12:30.958717Z","request_url": "http://127.0.0.1:4433/self-service/registration/browser","ui": {"action": "http://127.0.0.1:4433/self-service/registration?flow=74c643a1-f302-45c9-a760-1ad7b1157e1c","method": "POST","nodes": [{"type": "input","group": "default","attributes": {"name": "csrf_token","type": "hidden","value": "QQyUDHa4KJ3M6mowHHN4pboN4iaUOZL+4gYVtKYRWzSdWjSNcW5dG/SNzocyqqqAtV48KzQVMIC6X+Pv3tNPNw==","required": true,"disabled": false},"messages": [],"meta": {}}, {"type": "input","group": "password","attributes": {"name": "traits.email","type": "email","disabled": false},"messages": [],"meta": {"label": {"id": 1070002,"text": "E-Mail","type": "info"}}}, {...}]}
}

之后,依据流程信息创建表单:

<Card title="Register new account" bordered={false}>{/* 流程消息展示 */}{this.state.flow.ui.messages &&this.state.flow.ui.messages.map((m: UiText, index) => (<Alertkey={index}message={m.text}type={m.type as AlertProps["type"]}style={{ marginBottom: 16 }}showIcon/>))}{/* 流程表单创建 */}<Formname="register"ref={this.formRef}encType="application/x-www-form-urlencoded"action={this.state.flow.ui.action}method={this.state.flow.ui.method}onFinish={onFinish}>{this.state.flow.ui.nodes.map((node, index) => {return React.cloneElement(ui.toUiNodeAntd(node)!, {key: index,});})}</Form>
</Card>

其中表单 onFinish 里处理提交:

const onFinish = (values: any) => {// 因 AntD Form 不提交原 HTML form,所以自己创建 from 提交// - 不能直接 find form 提交,此时值已清空// - 创建 from 提交,与 AntD From 相互无影响ui.submitViaForm(this.state.flow!.ui, values);// 或者,用 `/self-service/registration/api` 提交// this.submitViaApi(values);
};

登录

  • GET /self-service/login/browser: 初始化登录流程
  • GET /self-service/login/flows: 获取登录流程
  • POST /self-service/login: 提交登录流程

与注册流程一样。

登录后,可通过 whoami 获取授权信息:

  • GET /sessions/whoami: 获取授权信息
authPublicApi.toSession(undefined, undefined, {withCredentials: true,}).then((res: AxiosResponse<Session>) => {if (utils.assertResponse(res)) {utils.redirectToSelfService("/self-service/login/browser");return;}this.setState({ session: res.data });}).catch((err: AxiosError) => utils.redirectOnError(err, "/auth/login"));

Dashboard 页展示了授权信息:

验证

  • GET /self-service/verification/browser: 初始化验证流程
  • GET /self-service/verification/flows: 获取验证流程
  • POST /self-service/verification: 提交验证流程

与注册流程一样。

恢复

  • GET /self-service/recovery/browser: 初始化恢复流程
  • GET /self-service/recovery/flows: 获取恢复流程
  • POST /self-service/recovery: 提交恢复流程

与注册流程一样。

设置

  • GET /self-service/settings/browser: 初始化设置流程
  • GET /self-service/settings/flows: 获取设置流程
  • POST /self-service/settings: 完成设置流程

与注册流程一样。

但要注意的是,依据流程信息创建表单时,请区分 group 构建多个表单:

const nodesGroup: Record<string,{title?: string;nodes?: Array<UiNode>;}
> = {default: {},profile: { title: "Profile" },password: { title: "Password" },oidc: { title: "Social Sign In" },
};
for (const [k, v] of Object.entries(nodesGroup)) {nodesGroup[k] = {title: v.title,nodes: ui.onlyNodes(this.state.flow!.ui.nodes, k),};
}
<Card title="Settings" bordered={false}>{this.state.flow.ui.messages &&this.state.flow.ui.messages.map((m: UiText, index) => (<Alertkey={index}message={m.text}type={m.type as AlertProps["type"]}style={{ marginBottom: 16 }}showIcon/>))}{/* Split Form by group here. Otherwise, one AntD Form method conflicts. */}{Object.entries(nodesGroup).filter(([k, v]) => k !== "default" && v && v.nodes!.length > 0).map(([k, v], index) => (<Formkey={index}name={k}encType="application/x-www-form-urlencoded"action={this.state.flow!.ui.action}method={this.state.flow!.ui.method}onFinish={onFinish}><Form.Item><div>{v.title}</div></Form.Item>{v.nodes!.concat(nodesGroup["default"].nodes!).map((node, index) => {return React.cloneElement(ui.toUiNodeAntd(node)!, {key: index,});})}</Form>))}
</Card>

登出

  • GET /self-service/logout/browser: 创建登出 URL
  • POST /self-service/logout: 完成登出流程

页面加载后创建登出 URL ,

authPublicApi.createSelfServiceLogoutFlowUrlForBrowsers(undefined, {withCredentials: true,}).then((res: AxiosResponse<SelfServiceLogoutUrl>) => {this.setState({ logoutUrl: res.data.logout_url });}).catch((err) => {// console.log(err);});

之后,页面加上登出按钮:

{this.state.logoutUrl && (<Buttontype="link"shape="circle"href={this.state.logoutUrl}icon={<LogoutOutlined />}/>
)}

参考

  • ORY Kratos ExpressJS Self-Service UI Reference
  • Kratos React Example

GoCoding 个人实践的经验分享,可关注公众号!


http://chatgpt.dhexx.cn/article/1Ro4O05T.shtml

相关文章

go微服务框架kratos 安装及使用

windows: 代理和mod 设置 set GO111MODULEonset GOPROXYhttps://goproxy.cn/ 安装protobuf库文件 go get -u github.com/golang/protobuf/proto 安装goprotobuf插件 go install github.com/golang/protobuf/protoc-gen-golatest 安装gogoprotobuf插件和依赖 go install gith…

go用户中心kratos

用户中心kratos kratos介绍 ORY Kratos是根据云架构最佳实践构建的API优先身份和用户管理系统。它实现了几乎每个软件应用程序都需要处理的核心用例&#xff1a; 自助登录和注册:允许最终用户使用用户名/电子邮件和密码组合,社交登录(使用Google&#xff0c;GitHub登录),无密码…

Kratos 集成Gin

Kratos 集成 Gin 规范项目分层处理请求处理、响应编写路由routeKratos 集成gin注入 wire set中 源码 Kratos 可以在 .proto文件定义请求类型&#xff0c;URL&#xff0c;响应等等&#xff0c;如官方示例&#xff1a; service BlogService {rpc CreateArticle (CreateArticleRe…

kratos mysql_Kratos--安装及配置

安装GO环境 安装protoc以及相关的包和插件 安装Kratos Go version>1.12 and GO111MODULEon go get -u github.com/bilibili/kratos/tool/kratos 提示&#xff1a;安装过程中可能会出现部分包下载失败&#xff0c;可以手动下载包然后拷贝至相应文件目录。 快速开始 cd $GOPAT…

初识go-kratos

推荐看一下 Kratos 官方文档 更加流畅观看此文章&#xff0c;本机器这里已经安装好了 kratos、proto、wire、make 等所需的命令工具 1.先下载beer-shop模板 git clone https://github.com/go-kratos/beer-shop.git 2.删除api和app下的全部文件 3.修改go.mod文件 把module g…

kratos mysql_kratos微服务框架学习笔记一(kratos-demo)

本文将为您描述kratos微服务框架学习笔记一(kratos-demo),教程操作步骤: 目录 kratos微服务框架学习笔记一(kratos-demo) kratos本体 demo kratos微服务框架学习笔记一(kratos-demo) 今年大部分时间飘过去了&#xff0c;没怎么更博和github&#xff0c;现在开发任务也差不多完成…

Kratos日志

一.如何在kratos框架中使用 参考官方文档中描述&#xff0c;为了方便业务自适配不同的 log 接入使用&#xff0c;Logger 只包含了最简单的 Log 接口。当业务需要在 Kratos 框架内部使用自定义的 log的时候&#xff0c;只需要简单实现方法即可。日志库较为公用建议放在kit基础库…

kratos框架学习,在Linux 下面使用kratos 创建demo 项目然后跑起来。使用 kratos new kratos-demo 一键创建项目,脚手架非常方便。但是依赖grpc没有起来

目录 前言1&#xff0c;关于kratos2&#xff0c;使用 kratos new kratos-demo 一键创建项目3&#xff0c;解决gRPC 编译问题4&#xff0c;只创建HTTP服务 前言 本文的原文连接是: https://blog.csdn.net/freewebsys/article/details/109139648 未经博主允许不得转载。 博主地址…

砥砺前行 | Kratos 框架 v2 版本架构演进之路

Kratos 是一套轻量级 Go 微服务框架&#xff0c;包含大量微服务相关功能及工具。名字来源于游戏《战神》&#xff0c;该游戏以希腊神话为背景&#xff0c;讲述了奎托斯&#xff08;Kratos&#xff09;由凡人成为战神并展开弑神屠杀的冒险历程。 写在前面 从 2021 年 2 月份&…

【kratos入门实战教程】1-kratos项目搭建和开发环境配置

1、系列目录 【kratos入门实战教程】0-商城项目介绍【kratos入门实战教程】1-kratos项目搭建和开发环境配置【kratos入门实战教程】2-实现注册登陆业务 2、概览 经过上一篇的说明&#xff0c;本篇教程正式开始搭建项目。深入解析工程项目的目录结构和介绍一些开发需要使用的工…

go微服务框架Kratos简单使用总结

Kratos是B站开源的一款go的微服务框架&#xff0c;最近PS5上的 战神诸神黄昏比较火&#xff0c;主角就是奎托斯。这个框架的名字就取自他。 在进行框架选型时&#xff0c;对比了目前主流的很多go微服务框架&#xff0c;如Zero&#xff0c;最后对比之下&#xff0c;选择了Krato…

c语言代码后return0表示什么意思,C语言中return 0 表示什么

满意答案 强计划止步不.. 2013.01.03 采纳率&#xff1a;44% 等级&#xff1a;12 已帮助&#xff1a;7948人 return表示函数结束, 也就是说CPU执行到return后, 就会跳转(如果要好理解的话, 是"回到")到调用它的地方, 然后继续执行. 而0, 是一个整型, 一般来说retu…

c语言代码后return0表示什么意思,return 0是什么意思 ?

return 0 代表告诉调用者程序是正常退出的。return是C预定义的语句&#xff0c;它提供了终止函数执行的一种方式。当return语句提供了一个值时&#xff0c;这个值就成为函数的返回值。 这个return语句结束main()函数的执行&#xff0c;把0返还给操作系统。从main()函数返回0表…

接口性能测试方案

一、 性能测试术语解释 1. 响应时间 响应时间即从应用系统发出请求开始&#xff0c;到客户端接收到最后一个字节数据为止所消耗的时间。响应时间按软件的特点再可以细分&#xff0c;如对于一个 C/S 软件&#xff08;B/S一样&#xff09;的响应时间可以细分为网络传输时间、应…

软件性能测试方案-性能测试准备

性能测试目的 1、性能调优 开发人员对系统调优后&#xff0c;需要测试人员配合去做性能测试&#xff0c;验证这次优化是否有效果。如果性能指标相比较之前的性能指标更好了&#xff0c;说明系统优化的有效果。反之说明调优不理想 2、新业务、新接口上线 系统从无到上线&…

参考文档一:性能测试---测试方案

性能测试详细测试方案 前言 平台XX项目系统已经成功发布&#xff0c;依据项目的规划&#xff0c;未来势必会出现业务系统中信息大量增长的态势。 随着业务系统在生产状态下日趋稳定、成熟&#xff0c;系统的性能问题也逐步成为了我们关注的焦点&#xff1a;每天大数据量的“…

【性能测试】性能测试方案设计

性能测试方案设计 1. 性能测试流程 系统架构调研 业务模型分析调研 测试需求分析设计测试方案测试环境搭建测试数据准备测试工具开发测试场景设置执行场景测试测试结果分析提交测试报告 2. 性能测试需求分析和范围确定 收集性能需求信息分析应用程序 系统设计和架构信息网…

接口性能测试方案 白皮书 V1.0

一、 性能测试术语解释 1. 响应时间 响应时间即从应用系统发出请求开始&#xff0c;到客户端接收到最后一个字节数据为止所消耗的时间。响应时间按软件的特点再可以细分&#xff0c;如对于一个 C/S 软件的响应时间可以细分为网络传输时间、应用服务器处理时间、数据库服务器处…

性能测试案例

做性能测试之前需要对Linux内核参数优化 Linux内核参数优化 Linux服务器默认支持1024个TCP链接&#xff0c;在性能测试时&#xff0c;无论压力机还是项目服务器&#xff0c;都需要对tcp参数进行一些优化 ulimit -n&#xff1a;查看当前Linux系统最大的连接数 修改Linux系统允许…

性能测试(一)

一)谈谈你对于性能测试的理解: 1)性能测试的概念 测试目的与功能测试的区别性能测试的指标 2)性能测试需要借助工具来进行测试&#xff0c;可以说说自己是用了哪些工具以及如何使用工具来进行性能测试 3)为了避免面试官在性能测试方面进行深究&#xff0c;主动说性能测试难就难…