企业SAML单点登录:实时口罩检测-通用Gradio集成Okta认证教程
企业SAML单点登录实时口罩检测-通用Gradio集成Okta认证教程1. 引言当AI应用遇上企业级安全想象一下这个场景你为公司的办公大楼部署了一套智能口罩检测系统用于访客管理和内部安全。系统运行得很好但每次员工或访客使用前都需要单独登录一次既麻烦又增加了IT部门管理账号的负担。更关键的是如何确保只有授权人员才能访问这个系统这正是我们今天要解决的问题。本文将手把手教你如何为基于ModelScope和Gradio部署的“实时口罩检测-通用”模型服务集成企业级的Okta单点登录认证。通过SAML协议你可以让员工使用公司统一的账号密码登录无需额外注册同时实现集中权限管理。学完这篇教程你将掌握如何理解SAML单点登录的核心流程。如何配置Okta作为身份提供商。如何改造Gradio应用使其支持SAML认证。最终实现一个既智能又安全的口罩检测企业应用。无论你是企业的开发人员、运维工程师还是对AI应用安全集成感兴趣的开发者这篇教程都将提供一条清晰的落地路径。我们不会涉及复杂的底层原理一切从“能用、好用”出发。2. 环境准备与项目概览在开始集成之前我们需要确保基础环境已经就绪并理解整个项目的架构。2.1 基础环境要求你需要准备以下环境一个可公网访问的服务器或云主机用于部署Gradio应用。本文假设你已通过ModelScope镜像部署了“实时口罩检测-通用”服务。一个Okta开发者账户可以免费注册用于创建和管理SAML应用。基本的Python开发环境服务器上需安装Python 3.8。网络连通性确保你的服务器可以访问互联网以下载依赖包和Okta服务。2.2 项目架构理解在集成认证前我们先快速回顾一下原始口罩检测服务的流程用户打开Gradio提供的Web界面。直接上传图片并点击检测。模型返回带检测框的结果图片。集成Okta SAML认证后流程将变为用户尝试访问Gradio应用。被重定向到Okta登录页面。用户使用企业账号登录Okta。Okta验证成功后将用户信息和认证断言“打包”发回Gradio应用。Gradio应用验证断言确认用户身份然后才展示主界面。用户进行口罩检测操作。整个过程中Gradio应用本身不存储和管理用户密码所有认证工作都委托给了Okta。3. 在Okta中配置SAML应用Okta将作为我们系统的“门卫”。首先我们需要在Okta中创建一个SAML应用并获取关键的配置信息。3.1 创建SAML应用登录你的Okta开发者控制台。在左侧导航栏进入Applications-Applications。点击Create App Integration按钮。在弹出的窗口中选择SAML 2.0作为登录方法然后点击Next。进入配置页面填写以下基本信息App name: 输入一个易于识别的名称例如口罩检测系统。App logo(可选): 可以上传一个图标。其他保持默认点击Next。3.2 配置SAML设置这是最关键的一步需要仔细填写。假设你的Gradio应用最终访问地址是https://your-server-ip:7860。在SAML Settings部分配置以下内容Single sign on URL: 填写https://your-server-ip:7860/saml/acs/这是Okta在用户登录后将认证信息SAML响应发送回来的地址。Audience URI (SP Entity ID): 填写https://your-server-ip:7860这是你的Gradio应用服务提供商的唯一标识符。Name ID format: 选择EmailAddress。Application username: 选择Email。Attribute statements(可选但推荐): 这里可以配置返回给应用的用户属性。点击Add Another设置Name:emailValue:user.email再添加一个Name:firstNameValue:user.firstName再添加一个Name:lastNameValue:user.lastName配置完成后页面大致如下所示请根据你的实际信息修改点击Next。3.3 完成配置并获取元数据在Feedback页面根据你的情况选择通常是I‘m an Okta customer adding an internal app然后点击Finish。应用创建成功后你会进入该应用的详情页。切换到Sign On标签页。在这里你可以找到最重要的信息SAML 2.0部分的配置。点击View SAML setup instructions。在弹出的页面中找到Provide the following IDP metadata to your SP provider部分。你需要复制两个关键信息Identity Provider Issuer: 通常是http://www.okta.com/xxxxxxxxxx格式的URL。Identity Provider Single Sign-On URL: Okta的登录端点。X.509 Certificate: 一大段PEM格式的证书内容。更简单的方法是直接下载元数据文件在Sign On标签页右侧找到SAML Metadata部分点击Download metadata file链接下载一个XML文件。这个文件包含了上面所有的信息我们后续会用到它。请保存好这些信息下一步配置Gradio应用时会使用。4. 改造Gradio应用集成SAML现在我们需要在部署了口罩检测模型的服务器上修改Gradio应用代码使其能够处理SAML认证。4.1 安装必要的Python库首先通过SSH连接到你的服务器进入Gradio应用所在的环境如果你使用了虚拟环境或容器请先激活。然后安装SAML认证所需的库。我们推荐使用python3-saml的Flask集成版。pip install flask flask-login python3-saml4.2 创建SAML认证中间件文件我们需要创建一个独立的Python文件来处理SAML相关的逻辑。在Gradio应用目录下例如/usr/local/bin/创建一个新文件命名为saml_auth.py。# saml_auth.py from flask import Flask, request, redirect, session, url_for from flask_login import LoginManager, UserMixin, login_user, logout_user, login_required, current_user from onelogin.saml2.auth import OneLogin_Saml2_Auth from onelogin.saml2.utils import OneLogin_Saml2_Utils import os # 初始化Flask应用和LoginManager auth_app Flask(__name__) auth_app.secret_key os.urandom(24) # 用于加密session生产环境请使用固定密钥 login_manager LoginManager() login_manager.init_app(auth_app) login_manager.login_view login # 指定未登录时重定向的视图 # 定义一个简单的用户类 class User(UserMixin): def __init__(self, user_id, attributes): self.id user_id self.email attributes.get(email, [])[0] self.first_name attributes.get(firstName, [])[0] self.last_name attributes.get(lastName, [])[0] login_manager.user_loader def load_user(user_id): # 这是一个简化示例。实际应用中你可能需要根据session或数据库加载用户 if samlUserdata in session: return User(user_id, session[samlUserdata]) return None # 准备SAML请求的环境字典 def prepare_flask_request(request): url_data request.url.split(?, 1) return { https: on if request.scheme https else off, http_host: request.host, server_port: request.environ.get(SERVER_PORT), script_name: request.path, get_data: request.args.copy(), post_data: request.form.copy(), query_string: request.query_string.decode(utf-8) if request.query_string else } # 加载SAML配置 # 注意你需要将下载的Okta元数据XML文件内容保存为 okta_metadata.xml 放在同级目录 # 或者直接使用配置字典。这里我们使用配置字典方式。 SAML_SETTINGS { strict: True, debug: True, # 调试阶段设为True生产环境设为False sp: { entityId: https://your-server-ip:7860, # 必须与Okta中配置的SP Entity ID一致 assertionConsumerService: { url: https://your-server-ip:7860/saml/acs/, # 必须与Okta中配置的Single sign on URL一致 binding: urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST }, singleLogoutService: { url: https://your-server-ip:7860/saml/sls/, binding: urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect }, NameIDFormat: urn:oasis:names:tc:SAML:1.1:nameid-format:emailAddress, x509cert: , # 服务提供商的证书可选如果不需要签名请求 privateKey: , # 服务提供商的私钥可选 }, idp: { entityId: http://www.okta.com/xxxxxxxxxx, # 替换为你的Okta Issuer singleSignOnService: { url: https://your-okta-domain.okta.com/app/your-app-name/xxxxxxxxxx/sso/saml, # 替换为你的Okta SSO URL binding: urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect }, singleLogoutService: { url: https://your-okta-domain.okta.com/app/your-app-name/xxxxxxxxxx/slo/saml, binding: urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect }, x509cert: -----BEGIN CERTIFICATE-----\nMIIDpDCCAoygAwIBAgIGAXb...你的Okta证书完整内容...nUca/DEs\n-----END CERTIFICATE----- # 替换为你的Okta证书 } } # 登录路由 - 发起SAML认证请求 auth_app.route(/saml/login) def login(): req prepare_flask_request(request) auth OneLogin_Saml2_Auth(req, old_settingsSAML_SETTINGS) return redirect(auth.login()) # ACS (Assertion Consumer Service) 路由 - 接收Okta的SAML响应 auth_app.route(/saml/acs/, methods[POST]) def acs(): req prepare_flask_request(request) auth OneLogin_Saml2_Auth(req, old_settingsSAML_SETTINGS) auth.process_response() errors auth.get_errors() if not errors: if auth.is_authenticated(): session[samlUserdata] auth.get_attributes() session[samlNameId] auth.get_nameid() session[samlSessionIndex] auth.get_session_index() # 创建用户并登录 user_id session[samlNameId] user User(user_id, session[samlUserdata]) login_user(user) # 登录成功后重定向到原始的Gradio应用主页面 return redirect(url_for(protected)) else: return 认证失败用户未通过验证。, 401 else: return f处理SAML响应时出错: {errors}, 500 # 受保护的主页即口罩检测界面 auth_app.route(/) login_required def protected(): # 这里原本应该返回Gradio的主界面。 # 实际上我们会将Gradio app作为这个路由的子应用挂载。 # 此处先返回一个简单页面后续步骤会整合。 return f h1欢迎, {current_user.first_name} {current_user.last_name} ({current_user.email})!/h1 p你已成功通过Okta登录。/p pa href/gradio进入口罩检测系统/a/p pa href/saml/logout退出登录/a/p # 登出路由 auth_app.route(/saml/logout) login_required def logout(): logout_user() session.clear() return redirect(url_for(login)) if __name__ __main__: auth_app.run(host0.0.0.0, port7860, debugTrue)重要提示你需要将SAML_SETTINGS字典中的your-server-ip、your-okta-domain、your-app-name、xxxxxxxxxx以及完整的x509cert证书内容替换为你在Okta配置中获取的实际值。4.3 修改主Gradio应用文件接下来我们需要修改原始的webui.py文件将其整合到我们的认证应用中。我们不是直接运行Gradio的launch()而是将其作为一个Flask蓝图或子应用。找到原始的webui.py文件路径可能是/usr/local/bin/webui.py在文件末尾修改启动部分。通常Gradio应用是通过demo.launch()启动的。我们需要将其改为创建gradio.Blocks或gradio.Interface对象然后由主Flask应用调用。假设原始webui.py的核心部分创建了一个名为demo的Gradio应用。我们做如下修改确保导入必要的库在文件开头添加。import gradio as gr from flask import Flask import sys import os sys.path.append(os.path.dirname(os.path.abspath(__file__))) from saml_auth import auth_app, login_required修改应用创建和启动逻辑找到if __name__ __main__:部分将其改为定义应用创建函数并移除demo.launch()。# ... 原有的模型加载和Gradio界面构建代码 ... # 假设构建好的Gradio界面对象是 demo # 将Gradio app挂载到Flask app上 app auth_app # 使用我们创建的认证Flask app # 创建一个函数来获取受保护的Gradio应用 app.route(/gradio) login_required def gradio_interface(): # 返回Gradio应用的本地渲染 # Gradio 3.x 之后支持与Flask更好的集成 # 这里我们使用 gr.Blocks 的 local_url 或直接挂载 # 更简单的方式将demo作为子应用挂载需要Gradio支持 # 由于Gradio的Flask集成方式可能变化这里提供一种通用思路 # 我们不再从这里启动而是修改saml_auth.py将demo整合进去。 return Gradio界面将在这里显示。 # 注释掉原有的启动代码 # demo.launch(server_name0.0.0.0, server_port7860) if __name__ __main__: # 现在启动的是集成了认证的Flask应用 app.run(host0.0.0.0, port7860, debugTrue)更优的整合方案由于Gradio内部也是基于Flask的更干净的做法是将Gradio的路由直接整合到saml_auth.py的Flask应用中并使用login_required装饰器保护所有Gradio的路由。这需要对Gradio的内部路由有一定了解。为了简化我们可以采用“网关”模式用户先访问认证应用7860端口认证后认证应用通过反向代理将请求转发到真正运行在另一个端口如7861的原始Gradio应用并在请求头中传递认证信息。但这涉及更多配置。为了本教程的简洁和可操作性我们采用一个折中但有效的方案修改saml_auth.py中的protected()视图使其直接返回一个包含Gradio应用iframe的页面。这样用户认证后页面内嵌的iframe会加载原始的Gradio服务。4.4 最终整合方案我们调整一下步骤采用以下结构保持原始Gradio服务运行在7861端口稍微修改原始webui.py让其运行在7861端口并且不直接对外网暴露通过设置shareFalse或仅监听本地。# 在原始 webui.py 的启动部分修改 if __name__ __main__: demo.launch(server_name127.0.0.1, server_port7861, shareFalse) # 只监听本地修改saml_auth.py中的受保护页面让protected()路由返回一个嵌入Gradio界面的HTML页面。auth_app.route(/) login_required def protected(): user_display_name f{current_user.first_name} {current_user.last_name} if current_user.first_name else current_user.email return f !DOCTYPE html html head title企业口罩检测系统/title style body {{ font-family: sans-serif; margin: 20px; }} .header {{ background-color: #f0f0f0; padding: 15px; border-radius: 5px; margin-bottom: 20px; }} .iframe-container {{ width: 100%; height: 80vh; border: 1px solid #ccc; border-radius: 5px; }} iframe {{ width: 100%; height: 100%; border: none; }} /style /head body div classheader h2企业智能口罩检测系统/h2 p欢迎 strong{user_display_name}/strong | a href/saml/logout退出登录/a/p p请在下方的界面中上传图片进行口罩检测。/p /div div classiframe-container iframe srchttp://127.0.0.1:7861/iframe /div /body /html 启动服务首先在终端1启动原始的口罩检测Gradio服务。cd /usr/local/bin python webui.py然后在终端2启动我们的SAML认证网关服务saml_auth.py。cd /usr/local/bin python saml_auth.py现在用户访问https://your-server-ip:7860时会先经过Okta认证认证成功后才能看到内嵌的口罩检测界面实际运行在7861端口。5. 测试与验证完成所有配置和代码修改后是时候进行测试了。5.1 分步测试流程访问应用在浏览器中打开https://your-server-ip:7860。重定向到Okta你应该被自动重定向到Okta的登录页面。输入企业账号使用你在Okta中配置的测试用户账号密码登录。跳转回应用登录成功后Okta会将你重定向回我们的应用 (/saml/acs/)该路由处理SAML响应并建立本地会话。进入主界面最后你被重定向到protected()路由看到欢迎信息和内嵌的口罩检测界面。功能测试在iframe内的Gradio界面中正常上传图片点击“开始检测”确认口罩检测功能正常工作。登出测试点击“退出登录”链接确认会话被清除再次访问根目录时会要求重新登录。5.2 常见问题排查错误SAML响应验证失败检查Okta中的Single sign on URL、Audience URI是否与SAML_SETTINGS中的配置完全一致包括HTTP/HTTPS。检查Okta的证书是否已正确复制到x509cert字段包含完整的-----BEGIN CERTIFICATE-----和-----END CERTIFICATE-----。错误用户属性未收到检查Okta中Attribute statements的配置确保Name和Value映射正确。在saml_auth.py的acs()函数中可以打印auth.get_attributes()来查看实际收到的属性。Gradio界面无法加载iframe内空白检查原始Gradio服务是否在127.0.0.1:7861上正常运行。检查服务器防火墙是否允许本地回环地址访问。可以在服务器上执行curl http://127.0.0.1:7861测试。登录后无限重定向检查auth_app.secret_key确保其值在每次应用重启后是固定的生产环境必须如此否则session会失效。同时检查Flask的SESSION_COOKIE_SECURE、SESSION_COOKIE_HTTPONLY等设置是否与你的部署环境HTTP/HTTPS匹配。6. 总结通过本教程我们成功地将一个开箱即用的AI模型服务——“实时口罩检测-通用”Gradio应用升级为了一个支持企业级单点登录的安全应用。我们利用了Okta作为身份提供商通过SAML 2.0协议实现了用户认证的集中化管理。回顾核心步骤规划与理解明确了SAML在服务提供商(SP)和身份提供商(IdP)之间的握手流程。配置IdP在Okta中创建并精细配置了SAML应用获取了元数据。改造SP使用Flask和python3-saml库构建了一个认证网关保护了原始的Gradio应用。集成与测试通过iframe方式将两个服务无缝结合并完成了端到端的测试。这种集成方式的价值在于提升安全性应用不处理密码降低了安全风险。改善体验用户无需记忆多套账号密码。便于管理管理员可以在Okta中心化地管理用户权限和生命周期。快速合规为满足企业内部安全审计要求提供了标准化的认证入口。你现在拥有的不再仅仅是一个AI模型演示而是一个可以正式部署到企业环境、具备基础安全准入能力的智能工具。你可以将此模式扩展到其他内部AI工具快速构建起统一认证的AI应用生态。获取更多AI镜像想探索更多AI镜像和应用场景访问 CSDN星图镜像广场提供丰富的预置镜像覆盖大模型推理、图像生成、视频生成、模型微调等多个领域支持一键部署。
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2416413.html
如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!