Open edX 本地 SAML 认证测试完全指南:使用 MockSAML 在 devstack 中配置与联调
Open edX 本地 SAML 认证测试完全指南使用 MockSAML 在 devstack 中配置与联调【免费下载链接】openedx-platformThe Open edX LMS Studio, powering education sites around the world!项目地址: https://gitcode.com/GitHub_Trending/ed/openedx-platform本篇指南基于 openedx-platform 仓库中的官方 HOW-TO 文档common/djangoapps/third_party_auth/docs/how_tos/testing_saml_locally.rst详细讲解如何在本地 Open edX devstack 环境中借助 MockSAML.com 这一免费测试身份提供商IdP搭建端到端的 SAML 单点登录链路。读完本文你将掌握 SAMLConfiguration、SAMLProviderConfig、SAMLProviderData 三个核心配置对象的正确配置方法、背后硬编码约束的源码依据以及完整的本地登录验证流程可复用于其他真实 IdP 的接入调试。为什么需要本地 SAML 测试SAMLSecurity Assertion Markup Language是教育机构接入单点登录的主流协议Open edX 以 Service ProviderSP身份与各类 Identity ProviderIdP对接。真实 IdP如学校统一认证平台往往部署在受限网络内联调周期长、日志不可见。MockSAML.com 提供了免费的 SAML 测试端点能在本地 devstack 中模拟完整的 SP → IdP 重定向 → 断言回传 → 用户落库流程是验证 Open edX 侧 SAML 配置是否正确的最快捷手段。SAML 认证的三个核心配置对象在 Open edX 中SAML 认证的正常工作依赖三个配置对象协同定义均位于 common/djangoapps/third_party_auth/models.py配置对象模型类职责SAMLConfigurationSAMLConfiguration(ConfigurationModel)models.py:473定义本 Open edX 实例作为 SP 的元数据实体 IDentity_id、密钥对private_key/public_key、组织信息org_info_str等SAMLProviderConfigSAMLProviderConfig(ProviderConfig)models.py:628定义某个具体 IdP 的连接信息实体 ID、元数据 URLmetadata_source、属性映射attr_email 等、各种跳过选项SAMLProviderDataSAMLProviderData(models.Model)models.py:925存储从 IdP 元数据端点抓取到的运行时数据SSO URL、签名公钥、有效期仅在真实认证过程中使用三者关系可以通过SAMLProviderConfig.get_config()models.py:862-922看得很清楚该方法取出 ProviderConfig 上的属性映射字段再以entity_id为键查询SAMLProviderDatamodels.py:898将公钥与 SSO URL 组装进conf最后通过self.saml_configuration or SAMLConfiguration.current(self.site.id, default)models.py:917-919挂上 SP 配置。关键硬编码约束SAMLConfiguration对象的 slug必须为default。这个值被硬编码在认证执行路径中当 ProviderConfig 未显式绑定 SAMLConfiguration 时代码会回退调用SAMLConfiguration.current(self.site.id, default)models.py:919provider.py 中SAMLConfiguration.is_enabled(..., default)、saml.py 中SAMLConfiguration.current(..., default)以及 views.py 中saml_config default均以default作为默认查找键。slug 不匹配将导致认证路径找不到 SP 配置直接报错或返回 404。前置条件本地 Open edX devstack 已启动并正常运行可访问 Django Admin 后台http://localhost:18000/admin/ 注册一个 MockSAML.com 账号免费的 SAML 测试服务了解 SAML 基础概念 中关于 SP/IdP 的角色划分。Step 1配置 SAMLConfigurationSP 侧SAMLConfiguration将 Open edX 实例声明为一个 SAML Service Provider是整套配置的地基。进入 Django Admin →Third Party Auth → SAML Configurations点击Add SAML Configuration按下表填写必填字段字段值Sitelocalhost:18000Slugdefault必须为default代码中硬编码见上文Entity IDhttps://saml.example.com/entityidEnabled✓勾选本地测试可留空密钥字段private_key与public_key留空即可。源码中SAMLConfiguration.get_setting()models.py:592-609在数据库字段为空时会回退读取 Django 设置SOCIAL_AUTH_SAML_SP_PUBLIC_CERT/SOCIAL_AUTH_SAML_SP_PRIVATE_KEYslug 为default时因此本地 MockSAML 场景下可以完全不配置密钥。若日后接入生产 IdP可用openssl req -new -x509 -days 3652 -nodes -out saml.crt -keyout saml.key生成密钥对并粘贴进去见 models.py:500-519 的字段帮助文本Organization Info可选可保持默认或自定义为{ en-US: { url: http://localhost:18000, displayname: Local Open edX, name: localhost } }该 JSON 会被get_setting(ORG_INFO)models.py:588-589解析写入 python-saml 生成的 SP 元数据的md:Organization节点默认值为{en-US: {url: http://www.example.com, displayname: Example Inc., name: example}}models.py:523字段定义中明确要求每个语言键下包含url、displayname、name三个子键点击Save保存。Step 2配置 SAMLProviderConfigIdP 侧SAMLProviderConfig负责建立到具体 IdP此处为 MockSAML的连接。进入 Django Admin →Third Party Auth → Provider Configuration (SAML IdP)点击Add Provider Configuration (SAML IdP)按下表填写字段值NameTest Localhost或任意描述性名称Slugdefault与测试 URL 保持一致Backend Nametpa-samlEntity IDhttps://saml.example.com/entityidMetadata Sourcehttps://mocksaml.com/api/saml/metadataSitelocalhost:18000SAML Configuration选择 Step 1 创建的 SAMLConfigurationEnabled✓勾选Visible☐测试阶段不勾选避免出现在登录页提供商列表中Skip hinted login dialog✓勾选推荐Skip registration form✓勾选推荐Skip email verification✓勾选推荐Send to registration first✓勾选推荐属性映射全部留空以使用默认值User ID、Email、Full Name 等SAMLProviderConfig上attr_user_permanent_id、attr_email、attr_full_name、attr_first_name、attr_last_name、attr_username等字段models.py:654-702留空后get_config()models.py:873-895会使用 python-social-auth 内置的default_email、default_full_name等默认属性名去 SAML 断言中取值点击Save保存。重要SAMLProviderConfig中的Entity ID 必须与 SAMLConfiguration 中的 Entity ID 完全一致本文均使用https://saml.example.com/entityid。因为认证时 IdP 元数据正是以entity_id为键从SAMLProviderData中查询的models.py:898且保存 ProviderConfig 时源码也会校验同名 entity_id 是否已被其他 slug 占用models.py:808-818。各勾选选项的源码含义Skip hinted login dialogmodels.py:730-737开启后访问带?tpa_hint[provider_name]的 URL 会直接跳转到 IdP 登录页不再弹出确认对话框Skip registration formmodels.py:738-745新用户认证后不再要求确认姓名、邮箱等资料直接完成注册仅建议用于可信任、能提供准确用户信息的 IdPSkip email verificationmodels.py:747-753用户注册后立即激活账号无需邮箱验证Send to registration firstmodels.py:754-760第三方认证成功后直接进入注册页而非登录页。Step 3设置 IdP DataSAMLProviderDataSAMLProviderData存放从 IdP 元数据端点获取的运行时信息。手动创建一条记录填写Entity IDhttps://saml.example.com/entityidSSO URLhttps://mocksaml.com/api/saml/ssoPublic KeyIdP 的签名证书从 MockSAML 元数据中提取Expires At设置为抓取时间起 1 年后例如抓取于 2026-02-27则设为 2027-02-27SAMLProviderData.is_valid()models.py:947-952会同时校验entity_id、sso_url、public_key三者非空且当前时间未超过expires_at任何一项不满足即视为无效。get_config()中只有is_valid()返回 True 的记录才会被采纳为签名公钥models.py:901-903若没有任何有效记录会抛出AuthNotConfigured并提示运行manage.py saml pullmodels.py:905-910。更推荐的自动化方式在实际场景中SAMLProviderData由系统自动抓取维护无需手填。在 Step 2 配置好Metadata Source后执行./manage.py lms saml --pull该命令实现于 common/djangoapps/third_party_auth/management/commands/saml.py会调用 tasks.py 中的fetch_saml_metadata()Celery 任务遍历所有启用的 ProviderConfig校验元数据 URL 后请求并解析 XML提取公钥、SSO URL 与过期时间写入SAMLProviderDatatasks.py:89-92。同时建议用manage.py saml --run-checks检查 ProviderConfig 与 SAMLConfiguration 的关联是否过期、site 是否匹配、是否存在缺失配置等问题saml.py:78-191。Step 4测试 SAML 认证流程浏览器访问http://localhost:18000/auth/idp_redirect/saml-default页面应 302 跳转到 MockSAML.com对应 IdP 登录页在 MockSAML 页面直接点击Sign In表单内已有预置测试用户数据认证完成后被重定向回 Open edX若是新用户会看到注册表单完成注册后即成功登录。该重定向端点由 views.py 中的IdPRedirectView提供URL 规则定义在 urls.pyauth/idp_redirect/slug:provider_slug。视图通过pipeline.get_login_url(provider_slug, ...)生成 IdP 登录 URLslug 不存在时返回 404URL 中的saml-前缀来自SAMLProviderConfig.prefix samlmodels.py:634与 slug 拼接而成的 provider_id。期望行为完整时序首次跳转至 MockSAMLhttps://mocksaml.com/api/saml/ssoMockSAML 展示登录页面用户完成认证后MockSAML 将 SAML 断言以 HTTP-POST 形式回传至 Open edX 的断言消费端点ACS URL见下文参考配置Open edX 侧SAMLAuthBackendsaml.pybackend 名为tpa-saml校验断言签名与有效期查找或创建对应用户用户被重定向至 dashboard老用户或注册表单新用户。参考配置一份可复现的完整示例以下是文档作者实测有效的完整配置快照可直接对照排错SAMLConfigurationid6Sitelocalhost:18000SlugdefaultEntity IDhttps://saml.example.com/entityidEnabledTrueSAMLProviderConfigid11NameTest LocalhostSlugdefaultEntity IDhttps://saml.example.com/entityidMetadata Sourcehttps://mocksaml.com/api/saml/metadataBackend Nametpa-samlSitelocalhost:18000SAML Configuration→ SAMLConfigurationid6EnabledTrueSAMLProviderDataid3Entity IDhttps://saml.example.com/entityidSSO URLhttps://mocksaml.com/api/saml/ssoPublic Key取自 MockSAML 元数据的签名证书Fetched At2026-02-27 18:05:4000:00Expires At2027-02-27 18:05:4100:00ValidTrueMockSAML 侧配置SP Entity IDhttps://saml.example.com/entityidACS URLhttp://localhost:18000/auth/complete/tpa-saml/auth/complete/tpa-saml/正是SAMLAuthBackend的断言消费端点其redirect_uri由saml_metadata_viewviews.py:97-100动态生成并写入 python-saml 的assertionConsumerService.url见 saml.py:70-74。Test User Attributesemail、firstName、lastName、uidMockSAML 返回的这组属性正好对应SAMLProviderConfig的默认属性映射无需在 admin 中额外配置。常见问题排查登录页上找不到测试 IdP确认SAMLProviderConfig的Visible未勾选测试阶段应保持不勾选或直接使用idp_redirectURL 绕过登录页入口Entity ID 不匹配导致断言被拒严格保持 SAMLConfiguration、SAMLProviderConfig、MockSAML 三处 Entity ID 完全一致本文均为https://saml.example.com/entityid报错 No SAMLProviderData found ... Run manage.py saml pullSAMLProviderData无有效记录或已过期运行./manage.py lms saml --pull重新抓取或检查手填记录中Public Key、SSO URL是否完整、Expires At是否已过期models.py:947-952slug 不是default导致 404/配置找不到将SAMLConfiguration.slug改回default——认证执行路径中SAMLConfiguration.current(site_id, default)是硬编码回退models.py:919断言回传异常开启SAMLProviderConfig的Debug Modemodels.py:716-722所有 SAML XML 请求与响应会被完整记录到日志便于定位签名或属性解析问题排查完毕后务必关闭。按照上述四步配置你即可在本地 devstack 中拥有一个可反复演练、日志透明的 SAML 联调环境将 MockSAML 替换为真实 IdP 的元数据端点后同一套配置思路可以直接迁移到生产接入。【免费下载链接】openedx-platformThe Open edX LMS Studio, powering education sites around the world!项目地址: https://gitcode.com/GitHub_Trending/ed/openedx-platform创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
上一篇/下一篇内容由系统自动关联
返回资讯列表 →