Help us learn about your current experience with the documentation. Take the survey.

认证

为获得完整覆盖,DAST 分析器必须与被测应用进行认证。这需要在 DAST CI/CD 作业中配置认证凭据和认证方法。

DAST 需要认证以实现以下目的:

  • 模拟真实攻击并识别可能被攻击者利用的漏洞。
  • 测试仅在认证后可见的用户特定功能和自定义行为。

DAST 作业通过在浏览器中填写并提交登录表单来向应用进行认证。提交表单后,DAST 作业会确认认证是否成功。如果认证成功,DAST 作业会继续执行,并保存凭据以便在爬取目标应用时重用。如果失败,DAST 作业将停止。

DAST 支持的认证方法包括:

  • 单步登录表单
  • 多步登录表单
  • 对配置的目标 URL 外部 URL 进行认证

选择认证凭据时:

  • 切勿使用对生产系统、生产服务器或访问生产数据有效的凭据。
  • 切勿对生产服务器运行认证扫描。认证扫描可能执行认证用户可执行的任何功能,包括修改或删除数据、提交表单和点击链接。仅对非生产系统或服务器运行认证扫描。
  • 提供允许 DAST 测试整个应用的凭据。
  • 记录凭据的到期日期(如有),以备将来参考。例如,使用 1Password 等密码管理器。

下图说明了认证不同阶段使用认证变量的方式:

%%{init: { "fontFamily": "GitLab Sans" }}%%
sequenceDiagram
    accTitle: 认证变量
    accDescr: 展示认证不同阶段认证变量的序列图。
    participant DAST
    participant Browser
    participant Target

    Note over DAST,Target: 初始化
    DAST->>Browser: 使用代理初始化浏览器
    DAST->>Browser: 导航至 DAST_AUTH_URL
    Browser->>Target: 加载初始页面
    Target-->>Browser: 返回页面内容(可能不包含登录表单)

    Note over DAST,Target: 处理登录前操作
    DAST->>Browser: 点击 DAST_AUTH_BEFORE_LOGIN_ACTIONS 指定的元素
    Browser->>Target: 发送点击操作
    Target-->>Browser: 渲染登录表单(模态框/页面)

    Note over DAST,Target: 认证
    DAST->>Browser: 填充 DAST_AUTH_USERNAME & DAST_AUTH_PASSWORD
    DAST->>Browser: 点击“提交”
    Browser->>Target: 提交表单
    Target-->>Browser: 处理认证
    Target-->>Browser: 设置认证令牌

    Note over DAST,Target: 处理登录后操作(如指定)
    DAST->>Browser: 执行 DAST_AUTH_AFTER_LOGIN_ACTIONS
    Browser->>Target: 登录后但在登录验证前的操作

    Note over DAST,Target: 验证
    DAST->>Browser: 检查 URL 是否匹配 DAST_AUTH_SUCCESS_IF_AT_URL(如配置)
    DAST->>Browser: 检查元素是否存在 DAST_AUTH_SUCCESS_IF_ELEMENT_FOUND(如配置)
    DAST->>Browser: 检查登录表单不存在 DAST_AUTH_SUCCESS_IF_NO_LOGIN_FORM(默认为 true)

入门指南

您应定期确认分析器的认证是否仍正常工作,因为应用变更可能导致认证随时间失效。

运行 DAST 认证扫描的步骤:

  • 阅读认证的先决条件
  • 更新目标网站为认证用户的落地页。
  • 如果登录表单的用户名、密码和提交按钮在同一页面,使用CI/CD 变量配置单步登录表单认证。
  • 如果登录表单的用户名和密码字段在不同页面,使用CI/CD 变量配置多步登录表单认证。
  • 确保扫描过程中用户不会登出

先决条件

  • 您拥有扫描时用于认证的用户名和密码。
  • 您已检查已知问题,确保 DAST 能认证到您的应用。
  • 如果您使用表单认证,您已满足先决条件。
  • 如果您的表单认证流程包含基于时间的一次性密码,您已满足额外先决条件。
  • 您已考虑如何验证认证是否成功。

表单认证

  • 您知道应用登录表单的 URL。或者,您知道如何从认证 URL 导航到登录表单(参见点击进入登录表单)。
  • 您知道 DAST 用于输入相应值的用户名和密码 HTML 字段的选择器
  • 您知道提交登录表单的元素的选择器

TOTP 认证

  • 您拥有测试用户 TOTP 注册的密钥(Base32 编码)。
  • 您已确认认证提供商支持以下 TOTP 配置(与 Google Authenticator 相同):
    • HMAC 算法:SHA-1
    • 时间步长:30 秒
    • 令牌长度:6
  • 您知道 DAST 用于输入生成的 TOTP 令牌的选择器
  • 您知道提交 TOTP 令牌的元素的选择器(如果与密码分开提交)。

可用 CI/CD 变量

有关 DAST 认证 CI/CD 变量列表,请参见认证变量

DAST CI/CD 变量表由 Rake 任务 bundle exec rake gitlab:dast_variables:compile_docs 生成。它使用 lib/gitlab/security/dast_variables.rb 中定义的变量元数据。

更新目标网站

使用 CI/CD 变量 DAST_TARGET_URL 定义的目标网站是 DAST 开始爬取您应用的 URL。

为获得认证扫描的最佳爬取结果,目标网站应是用户认证后才能访问的 URL。通常,这是用户登录后着陆的页面 URL。

例如:

include:
  - template: DAST.gitlab-ci.yml

dast:
  variables:
    DAST_TARGET_URL: "https://example.com/dashboard/welcome"
    DAST_AUTH_URL: "https://example.com/login"

HTTP 认证配置

要使用 HTTP 认证方案(如基本认证),您可以将 DAST_AUTH_TYPE 值设置为 basic-digest。其他方案(如 Negotiate 或 NTLM)可能可用,但因当前缺乏自动化测试覆盖而不被正式支持。

配置需要为 DAST 作业定义 CI/CD 变量 DAST_AUTH_TYPEDAST_AUTH_URLDAST_AUTH_USERNAMEDAST_AUTH_PASSWORD。如果您没有唯一的登录 URL,请将 DAST_AUTH_URL 设置为与 DAST_TARGET_URL 相同的 URL。

include:
  - template: DAST.gitlab-ci.yml

dast:
  variables:
    DAST_TARGET_URL: "https://example.com"
    DAST_AUTH_TYPE: "basic-digest"
    DAST_AUTH_URL: "https://example.com"

切勿在 YAML 作业定义文件中定义 DAST_AUTH_USERNAMEDAST_AUTH_PASSWORD,因为这可能带来安全风险。相反,请使用 GitLab UI 将它们创建为屏蔽的 CI/CD 变量。 更多信息请参见自定义 CI/CD 变量

单步登录表单配置

单步登录表单的所有登录表单元素都在同一页面上。 配置需要为 DAST 作业定义 CI/CD 变量 DAST_AUTH_URLDAST_AUTH_USERNAMEDAST_AUTH_USERNAME_FIELDDAST_AUTH_PASSWORDDAST_AUTH_PASSWORD_FIELDDAST_AUTH_SUBMIT_FIELD

您应在作业定义 YAML 中设置 URL 和字段选择器,例如:

include:
  - template: DAST.gitlab-ci.yml

dast:
  variables:
    DAST_TARGET_URL: "https://example.com"
    DAST_AUTH_URL: "https://example.com/login"
    DAST_AUTH_USERNAME_FIELD: "css:[name=username]"
    DAST_AUTH_PASSWORD_FIELD: "css:[name=password]"
    DAST_AUTH_SUBMIT_FIELD: "css:button[type=submit]"

切勿在 YAML 作业定义文件中定义 DAST_AUTH_USERNAMEDAST_AUTH_PASSWORD,因为这可能带来安全风险。相反,请使用 GitLab UI 将它们创建为屏蔽的 CI/CD 变量。 更多信息请参见自定义 CI/CD 变量

多步登录表单配置

多步登录表单包含两个页面。第一页包含一个带有用户名和“下一步”提交按钮的表单。如果用户名有效,后续页面的第二个表单包含密码和表单提交按钮。

配置需要为 DAST 作业定义以下 CI/CD 变量:

  • DAST_AUTH_URL
  • DAST_AUTH_USERNAME
  • DAST_AUTH_USERNAME_FIELD
  • DAST_AUTH_FIRST_SUBMIT_FIELD
  • DAST_AUTH_PASSWORD
  • DAST_AUTH_PASSWORD_FIELD
  • DAST_AUTH_SUBMIT_FIELD

您应在作业定义 YAML 中设置 URL 和字段选择器,例如:

include:
  - template: DAST.gitlab-ci.yml

dast:
  variables:
    DAST_TARGET_URL: "https://example.com"
    DAST_AUTH_URL: "https://example.com/login"
    DAST_AUTH_USERNAME_FIELD: "css:[name=username]"
    DAST_AUTH_FIRST_SUBMIT_FIELD: "css:button[name=next]"
    DAST_AUTH_PASSWORD_FIELD: "css:[name=password]"
    DAST_AUTH_SUBMIT_FIELD: "css:button[type=submit]"

切勿在 YAML 作业定义文件中定义 DAST_AUTH_USERNAMEDAST_AUTH_PASSWORD,因为这可能带来安全风险。相反,请使用 GitLab UI 将它们创建为屏蔽的 CI/CD 变量。 更多信息请参见自定义 CI/CD 变量

基于时间的一次性密码 (TOTP) 配置

TOTP 配置需要为 DAST 作业定义以下 CI/CD 变量:

  • DAST_AUTH_OTP_FIELD
  • DAST_AUTH_OTP_KEY

如果 TOTP 令牌在提交密码后通过自己的表单提交,您还必须定义此变量:

  • DAST_AUTH_OTP_SUBMIT_FIELD

_FIELD 选择器变量可以在作业定义 YAML 中定义,例如:

include:
  - template: DAST.gitlab-ci.yml

dast:
  variables:
    DAST_TARGET_URL: "https://example.com"
    DAST_AUTH_URL: "https://example.com/login"
    DAST_AUTH_USERNAME_FIELD: "css:[name=username]"
    DAST_AUTH_PASSWORD_FIELD: "css:[name=password]"
    DAST_AUTH_SUBMIT_FIELD: "css:button[type=submit]"
    DAST_AUTH_OTP_FIELD: "name:otp"
    DAST_AUTH_OTP_SUBMIT_FIELD: "css:input[type=submit]"

切勿在 YAML 作业定义文件中定义 DAST_AUTH_OTP_KEY,因为这可能带来安全风险。相反,请使用 GitLab UI 将它创建为屏蔽的 CI/CD 变量。 更多信息请参见自定义 CI/CD 变量

单点登录 (SSO) 配置

如果用户可以登录应用,则在大多数情况下,DAST 也能登录。即使应用使用单点登录。使用 SSO 解决方案的应用应使用单步多步登录表单配置指南配置 DAST 认证。

DAST 支持用户被重定向到外部身份提供者站点进行登录的认证流程。 检查 DAST 认证的已知问题,以确定您的 SSO 认证流程是否受支持。

Windows 集成认证 (Kerberos) 配置

Windows 集成认证 (Kerberos) 是托管在 Windows 域内的业务线 (LOB) 应用常见的认证机制。它使用用户的计算机登录实现无认证提示。

要配置此认证形式,请执行以下步骤:

  1. 在 IT/运维团队的协助下收集必要信息。
  2. 在您的 .gitlab-ci.yml 文件中创建或更新 dast 作业定义。
  3. 使用收集的信息填充示例 krb5.conf 文件。
  4. 设置必要的作业变量。
  5. 通过项目 Settings 页面设置必要的秘密变量。
  6. 测试并验证认证功能是否正常。

在 IT/运维部门的协助下收集以下信息:

  • Windows 域或 Kerberos 领域的名称(名称中必须包含句点,如 EXAMPLE.COM
  • Windows/Kerberos 域控制器的主机名
  • 对于 Kerberos,认证服务器名称。对于 Windows 域,这是域控制器。

创建 krb5.conf 文件:

[libdefaults]
  # Realm 是域名称的另一种说法
  default_realm = EXAMPLE.COM
  # Windows 域不需要这些设置
  # 它们支持其他 Kerberos 实现
  kdc_timesync = 1
  ccache_type = 4
  forwardable = true
  proxiable = true
  rdns = false
  fcc-mit-ticketflags = true
[realms]
  EXAMPLE.COM = {
    # 域控制器或 KDC
    kdc = kdc.example.com
    # 域控制器或管理服务器
    admin_server = kdc.example.com
  }
[domain_realm]
  # 将 DNS 域映射到领域/Windows 域
  # DAST_AUTH_NEGOTIATE_DELEGATION 提供的 DNS 域也应在此处表示(但不包含通配符)
  .example.com = EXAMPLE.COM
  example.com = EXAMPLE.COM

此配置使用 DAST_AUTH_NEGOTIATE_DELEGATION 变量。 此变量设置允许集成认证所需的以下 Chromium 策略:

此变量的设置是与您的 Windows 域或 Kerberos 领域关联的 DNS 域。 您应提供:

  • 小写和大写形式。
  • 通配符模式和仅域名形式。

在我们的示例中,Windows 域是 EXAMPLE.COM,DNS 域是 example.com。 这为 DAST_AUTH_NEGOTIATE_DELEGATION 提供了值 *.example.com,example.com,*.EXAMPLE.COM,EXAMPLE.COM

将所有内容整合到作业定义中:

# 此作业将扩展 DAST 模板中定义的 dast 作业
# 该模板也必须包含在内。
dast:
  image:
    name: "$SECURE_ANALYZERS_PREFIX/dast:$DAST_VERSION$DAST_IMAGE_SUFFIX"
    docker:
      user: root
  variables:
    DAST_TARGET_URL: https://target.example.com
    DAST_AUTH_URL: https://target.example.com
    DAST_AUTH_TYPE: basic-digest
    DAST_AUTH_NEGOTIATE_DELEGATION: '*.example.com,example.com,*.EXAMPLE.COM,EXAMPLE.COM'
    # 未显示 -- DAST_AUTH_USERNAME, DAST_AUTH_PASSWORD 通过 Settings -> CI -> Variables 设置
  before_script:
    - KRB5_CONF='
[libdefaults]
  default_realm = EXAMPLE.COM
  kdc_timesync = 1
  ccache_type = 4
  forwardable = true
  proxiable = true
  rdns = false
  fcc-mit-ticketflags = true
[realms]
  EXAMPLE.COM = {
    kdc = ad1.example.com
    admin_server = ad1.example.com
  }
[domain_realm]
  .example.com = EXAMPLE.COM
  example.com = EXAMPLE.COM
'
    - cat "$KRB5_CONF" > /etc/krb5.conf
    - echo '$DAST_AUTH_PASSWORD' | kinit $DAST_AUTH_USERNAME
    - klist

预期输出:

作业控制台输出包含 before 脚本的输出。如果认证成功,它将类似于以下内容。如果认证失败,作业将停止运行扫描。

Password for [email protected]:
Ticket cache: FILE:/tmp/krb5cc_1000
Default principal: [email protected]

Valid starting       Expires              Service principal
11/11/2024 21:50:50  11/12/2024 07:50:50  krbtgt/[email protected]
        renew until 11/12/2024 21:50:50

DAST 扫描器还将输出以下内容,表示成功:

2024-11-08T17:03:09.226 INF AUTH  正在尝试认证 find_auth_fields="basic-digest"
2024-11-08T17:03:09.226 INF AUTH  加载登录页面 LoginURL="https://target.example.com"
2024-11-08T17:03:10.619 INF AUTH  验证登录尝试是否成功 true_when="HTTP 状态码 < 400 且存在认证令牌且未检测到登录表单(自动检测)"
2024-11-08T17:03:10.619 INF AUTH  满足要求,HTTP 登录请求返回状态码 200 want="HTTP 状态码 < 400" url="https://target.example.com/"
2024-11-08T17:03:10.623 INF AUTH  满足要求,未检测到登录表单 want="未检测到登录表单(自动检测)"
2024-11-08T17:03:10.623 INF AUTH  认证令牌 cookies 名称=""
2024-11-08T17:03:10.623 INF AUTH  认证令牌存储事件键=""
2024-11-08T17:03:10.623 INF AUTH  满足要求,检测到基本认证 want="存在认证令牌"
2024-11-08T17:03:11.230 INF AUTH  登录尝试成功

点击进入登录表单

定义 DAST_AUTH_BEFORE_LOGIN_ACTIONS 以提供从 DAST_AUTH_URL 点击元素的路径,使 DAST 能够访问登录表单。此方法适用于在弹出窗口(模态框)中显示登录表单或登录表单没有唯一 URL 的应用。

例如:

include:
  - template: DAST.gitlab-ci.yml

dast:
  variables:
    DAST_TARGET_URL: "https://example.com"
    DAST_AUTH_URL: "https://example.com/login"
    DAST_AUTH_BEFORE_LOGIN_ACTIONS: "css:.navigation-menu,css:.login-menu-item"

提交登录表单后执行额外操作

定义 DAST_AUTH_AFTER_LOGIN_ACTIONS 以提供在提交登录表单后、验证前执行的操作序列,此时认证详细信息被记录。 这可用于通过“保持登录”对话框。

操作 格式
点击元素 click(on=<selector>)
从下拉列表中选择选项 select(option=<selector>)

操作以逗号分隔。有关选择器的信息,请参见查找元素的选择器

例如:

include:
  - template: DAST.gitlab-ci.yml

dast:
  variables:
    DAST_TARGET_URL: "https://example.com"
    DAST_AUTH_URL: "https://example.com/login"
    DAST_AUTH_AFTER_LOGIN_ACTIONS: "select(option=id:accept-yes),click(on=id:continue-button)"

排除登出 URL

如果 DAST 在运行认证扫描时爬取登出 URL,用户将被登出,导致扫描其余部分未认证。 因此,建议使用 CI/CD 变量 DAST_SCOPE_EXCLUDE_URLS 排除登出 URL。DAST 不会访问任何排除的 URL,确保用户保持登录状态。

提供的 URL 可以是绝对 URL,或相对于 DAST_TARGET_URL 基础路径的 URL 路径正则表达式。例如:

include:
  - template: DAST.gitlab-ci.yml

dast:
  variables:
    DAST_TARGET_URL: "https://example.com/welcome/home"
    DAST_SCOPE_EXCLUDE_URLS: "https://example.com/logout,/user/.*/logout"

查找元素的选择器

选择器由 CI/CD 变量使用,以指定浏览器中显示的元素位置。 选择器格式为 type:search string。DAST 根据类型使用搜索字符串搜索选择器。

选择器类型 示例 描述
css css:.password-field 搜索具有提供 CSS 选择器的 HTML 元素。出于性能考虑,选择器应尽可能具体。
id id:element 搜索具有提供元素 ID 的 HTML 元素。
name name:element 搜索具有提供元素名称的 HTML 元素。
xpath xpath://input[@id="my-button"]/a 搜索具有提供 XPath 的 HTML 元素。XPath 预期性能低于其他搜索。

使用 Google Chrome 查找选择器

Chrome DevTools 元素选择器工具是查找选择器的有效方法。

  1. 打开 Chrome 并导航到您要查找选择器的页面,例如您网站的登录页面。
  2. 使用键盘快捷键 Command + Shift + c (macOS) 或 Ctrl + Shift + c (Windows/Linux) 在 Chrome DevTools 中打开 Elements 选项卡。
  3. 选择 Select an element in the page to select it 工具。 search-elements
  4. 选择您页面上要了解选择器的字段。
  5. 工具激活后,高亮显示您要查看详细信息的字段。 highlight
  6. 高亮后,您可以看到元素的详细信息,包括可能适合作为选择器的属性。

在此示例中,id="user_login" 似乎是良好的候选选择器。您可以通过设置 DAST_AUTH_USERNAME_FIELD: "id:user_login" 将其用作 DAST 用户名字段的选择器。

选择正确的选择器

明智的选择器选择可使扫描对应用变更具有弹性。

按优先顺序,您应选择:

  • id 字段。这些字段在页面上通常是唯一的,且很少变更。
  • name 字段。这些字段在页面上通常是唯一的,且很少变更。
  • 特定于字段的 class 值,例如用户名字段上 "css:.username"username 类的选择器。
  • 字段特定的数据属性存在,例如当 data-username 字段在用户名字段上有任何值时,选择器 "css:[data-username]"
  • 多个 class 层级值,例如当存在多个具有 username 类的元素但只有一个嵌套在具有 login-form 类的元素内时,选择器 "css:.login-form .username"

当使用选择器定位特定字段时,应避免搜索:

  • 任何动态生成的 idnameattributeclassvalue
  • 通用类名,如 column-10dark-grey
  • XPath 搜索,因为它们比其他选择器搜索性能更低。
  • 无范围搜索,如以 css:*xpath://* 开头的搜索。

验证认证成功

DAST 提交登录表单后,会进行验证过程以确定认证是否成功。如果认证失败,扫描将停止并报错。

提交登录表单后,认证被确定为失败的情况包括:

  • 登录提交 HTTP 响应的状态码为 400500 系列。
  • 任何验证检查失败。
  • 认证过程中未设置具有足够随机值的认证令牌

验证检查

验证检查在认证完成后检查浏览器状态,以进一步确定认证是否成功。

如果未配置验证检查,DAST 会测试登录表单是否存在。

基于 URL 验证

定义 DAST_AUTH_SUCCESS_IF_AT_URL 为登录表单成功提交后浏览器选项卡中显示的 URL。

DAST 将验证 URL 与认证后浏览器中的 URL 进行比较。如果它们不相同,认证失败。

例如:

include:
  - template: DAST.gitlab-ci.yml

dast:
  variables:
    DAST_TARGET_URL: "https://example.com"
    DAST_AUTH_SUCCESS_IF_AT_URL: "https://example.com/user/welcome"

基于元素存在验证

定义 DAST_AUTH_SUCCESS_IF_ELEMENT_FOUND 为一个选择器,用于在登录表单成功提交后显示的页面上查找一个或多个元素。如果未找到元素,认证失败。在登录失败时显示的页面上搜索选择器应不返回任何元素。

例如:

include:
  - template: DAST.gitlab-ci.yml

dast:
  variables:
    DAST_TARGET_URL: "https://example.com"
    DAST_AUTH_SUCCESS_IF_ELEMENT_FOUND: "css:.welcome-user"

基于登录表单不存在验证

定义 DAST_AUTH_SUCCESS_IF_NO_LOGIN_FORM"true",表示 DAST 应在登录表单成功提交后显示的页面上搜索登录表单。如果登录后仍存在登录表单,认证失败。

例如:

include:
  - template: DAST.gitlab-ci.yml

dast:
  variables:
    DAST_TARGET_URL: "https://example.com"
    DAST_AUTH_SUCCESS_IF_NO_LOGIN_FORM: "true"

认证令牌

DAST 记录认证过程中设置的认证令牌。 认证令牌在 DAST 打开新浏览器时被加载,以便用户在整个扫描过程中保持登录状态。

为记录令牌,DAST 在认证过程前对应用设置的 cookies、本地存储和会话存储值进行快照。DAST 在认证后也执行相同操作,并使用差异来确定哪些是由认证过程创建的。

DAST 将使用足够“随机”值设置的 cookies、本地存储和会话存储值视为认证令牌。例如,sessionID=HVxzpS8GzMlPAc2e39uyIVzwACIuGe0H 将被视为认证令牌,而 ab_testing_group=A1 则不会。

CI/CD 变量 DAST_AUTH_COOKIE_NAMES 可用于指定认证 cookie 的名称,并绕过 DAST 使用的随机性检查。这不仅能使认证过程更健壮,还能提高检查认证令牌的漏洞检查准确性。

例如:

include:
  - template: DAST.gitlab-ci.yml

dast:
  variables:
    DAST_TARGET_URL: "https://example.com"
    DAST_AUTH_COOKIE_NAMES: "sessionID,refreshToken"

已知问题

  • 如果认证流程包含 CAPTCHA,DAST 无法绕过。 为被扫描应用在测试环境中为配置的用户关闭此功能。
  • DAST 无法使用短信或生物识别进行一次性密码 (OTP) 认证。 为被扫描应用在测试环境中为配置的用户关闭此功能;或将用户的 MFA 类型更改为 TOTP。
  • DAST 无法认证到登录期间未设置认证令牌的应用。
  • DAST 无法认证到需要比用户名、密码和可选 TOTP 更多文本输入的应用。

故障排除

日志提供了 DAST 在认证过程中的操作和期望的洞察。有关更详细的信息,请配置认证报告

有关特定错误消息或情况的信息,请参见已知问题

使用基于浏览器的分析器进行用户认证。有关高级故障排除,请参见基于浏览器的故障排除

读取日志

DAST CI/CD 作业的控制台输出使用 AUTH 日志模块显示认证过程信息。例如,以下日志显示多步登录表单的认证失败。 认证失败是因为登录后应显示主页,但登录表单仍然存在。

2022-11-16T13:43:02.000 INF AUTH  正在尝试认证
2022-11-16T13:43:02.000 INF AUTH  加载登录页面 LoginURL=https://example.com/login
2022-11-16T13:43:10.000 INF AUTH  检测到多步认证
2022-11-16T13:43:15.000 INF AUTH  验证用户提交是否成功 true_when="HTTP 状态码 < 400"
2022-11-16T13:43:15.000 INF AUTH  满足要求,未检测到登录 HTTP 消息 want="HTTP 状态码 < 400"
2022-11-16T13:43:20.000 INF AUTH  验证登录尝试是否成功 true_when="HTTP 状态码 < 400 且存在认证令牌且未检测到登录表单(未使用选择器 css:[id=email] 或 css:[id=password] 或 css:[id=submit] 搜索到元素)"
2022-11-24T14:43:20.000 INF AUTH  满足要求,HTTP 登录请求返回状态码 200 url=https://example.com/user/login?error=invalid%20credentials want="HTTP 状态码 < 400"
2022-11-16T13:43:21.000 INF AUTH  不满足要求,检测到登录表单 want="未检测到登录表单(未使用选择器 css:[id=email] 或 css:[id=password] 或 css:[id=submit] 搜索到元素)"
2022-11-16T13:43:21.000 INF AUTH  登录尝试失败 error="认证失败:无法认证用户"

配置认证报告

认证报告可能包含执行登录所使用的凭据等敏感信息。

认证报告可保存为 CI/CD 作业工件,以帮助理解认证失败的原因。

报告包含登录过程中执行的步骤、HTTP 请求和响应、文档对象模型 (DOM) 和截图。

dast-auth-report

导出认证调试报告的示例配置可能如下所示:

dast:
  variables:
    DAST_TARGET_URL: "https://example.com"
    DAST_AUTH_REPORT: "true"

已知问题

登录表单未找到

加载登录页面时 DAST 未找到登录表单,通常是因为无法加载认证 URL。 日志报告致命错误,例如:

2022-12-07T12:44:02.838 INF AUTH  加载登录页面 LoginURL=[认证 URL]
2022-12-07T12:44:11.119 FTL MAIN  认证失败:未找到登录表单

建议操作:

  • 生成认证报告以检查 HTTP 响应。
  • 检查目标应用认证是否已部署并运行。
  • 检查 DAST_AUTH_URL 是否正确。
  • 检查 GitLab Runner 是否可以访问 DAST_AUTH_URL
  • 如果使用了 DAST_AUTH_BEFORE_LOGIN_ACTIONS,检查其是否有效。

扫描未爬取认证页面

如果 DAST 在认证过程中捕获了错误的认证令牌,则扫描无法爬取认证页面。认证令牌的名称和存储令牌会写入日志。例如:

2022-11-24T14:42:31.492 INF AUTH  认证令牌 cookies 名称=["sessionID"]
2022-11-24T14:42:31.492 INF AUTH  认证令牌存储事件键=["token"]

建议操作:

  • 生成认证报告并查看 Login submit 的截图,验证登录是否按预期工作。
  • 验证记录的认证令牌是否是您的应用使用的令牌。
  • 如果使用 cookies 存储认证令牌,请使用 DAST_AUTH_COOKIE_NAMES 设置认证令牌 cookie 的名称。

无法使用选择器找到元素

DAST 未找到用户名、密码、第一个提交按钮或提交按钮元素。日志报告致命错误,例如:

2022-12-07T13:14:11.545 FTL MAIN  认证失败:无法使用选择器找到元素:css:#username

建议操作:

  • 生成认证报告以使用 Login page 的截图验证页面是否正确加载。
  • 在浏览器中加载登录页面,并验证 DAST_AUTH_USERNAME_FIELDDAST_AUTH_PASSWORD_FIELDDAST_AUTH_FIRST_SUBMIT_FIELDDAST_AUTH_SUBMIT_FIELD 中配置的选择器是否正确。

无法认证用户

DAST 因登录验证检查失败而认证失败。日志报告致命错误,例如:

2022-12-07T06:39:49.483 INF AUTH  验证登录尝试是否成功 true_when="HTTP 状态码 < 400 且存在认证令牌且未检测到登录表单(未使用选择器 css:[name=username] 或 css:[name=password] 或 css:button[type=\"submit\"] 搜索到元素)"
2022-12-07T06:39:49.484 INF AUTH  满足要求,HTTP 登录请求返回状态码 303 url=http://auth-manual:8090/login want="HTTP 状态码 < 400"
2022-12-07T06:39:49.513 INF AUTH  不满足要求,检测到登录表单 want="未检测到登录表单(未使用选择器 css:[name=username] 或 css:[name=password] 或 css:button[type=\"submit\"] 搜索到元素)"
2022-12-07T06:39:49.589 INF AUTH  登录尝试失败 error="认证失败:无法认证用户"
2022-12-07T06:39:53.626 FTL MAIN  认证失败:无法认证用户

建议操作:

  • 在日志中查找 requirement is unsatisfied。响应相应的错误。

不满足要求,检测到登录表单

通常,用户登录后会显示仪表板,而用户名或密码错误时会显示带有错误消息的登录表单。

当 DAST 在用户认证后显示的页面上检测到登录表单时,会发生此错误,表明登录尝试失败。

2022-12-07T06:39:49.513 INF AUTH  不满足要求,检测到登录表单 want="未检测到登录表单(未使用选择器 css:[name=username] 或 css:[name=password] 或 css:button[type=\"submit\"] 搜索到元素)"

建议操作:

  • 验证使用的用户名和密码/认证凭据是否正确。
  • 生成认证报告并验证 Login submitRequest 是否正确。
  • 认证报告 Login submit 的请求和响应可能为空。当没有会导致页面完全重新加载的请求时会发生这种情况,例如提交 HTML 表单时发出的请求。当使用 websockets 或 AJAX 提交登录表单时会发生这种情况。
  • 如果用户认证后显示的页面确实包含与登录表单选择器匹配的元素,请配置 DAST_AUTH_SUCCESS_IF_AT_URLDAST_AUTH_SUCCESS_IF_ELEMENT_FOUND 以使用替代方法验证登录尝试。

不满足要求,选择器未返回结果

DAST 在用户登录后显示的页面上找不到与 DAST_AUTH_SUCCESS_IF_ELEMENT_FOUND 中提供的选择器匹配的元素。

2022-12-07T06:39:33.239 INF AUTH  不满足要求,使用选择器搜索 DOM 未返回结果 want="存在元素 css:[name=welcome]"

建议操作:

  • 生成认证报告并查看 Login submit 的截图,验证是否显示了预期页面。
  • 确保 DAST_AUTH_SUCCESS_IF_ELEMENT_FOUND选择器正确。

不满足要求,浏览器不在指定 URL

DAST 检测到用户登录后显示的页面的 URL 与根据 DAST_AUTH_SUCCESS_IF_AT_URL 期望的 URL 不同。

2022-12-07T11:28:00.241 INF AUTH  不满足要求,浏览器不在指定 URL browser_url="https://example.com/home" want="位于 url https://example.com/user/dashboard"

建议操作:

  • 生成认证报告并查看 Login submit 的截图,验证是否显示了预期页面。
  • 确保 DAST_AUTH_SUCCESS_IF_AT_URL 正确。

不满足要求,HTTP 登录请求状态码

加载登录表单或提交表单时的 HTTP 响应状态码为 400(客户端错误)或 500(服务器错误)。

2022-12-07T06:39:53.626 INF AUTH  不满足要求,HTTP 登录请求返回状态码 502 url="https://example.com/user/login" want="HTTP 状态码 < 400"
  • 验证使用的用户名和密码/认证凭据是否正确。
  • 生成认证报告并验证 Login submitRequest 是否正确。
  • 验证目标应用是否按预期工作。

不满足要求,未检测到认证令牌

DAST 无法检测到认证过程中创建的认证令牌

2022-12-07T11:25:29.010 INF AUTH  认证令牌 cookies 名称=[]
2022-12-07T11:25:29.010 INF AUTH  认证令牌存储事件键=[]
2022-12-07T11:25:29.010 INF AUTH  不满足要求,未检测到基本认证、cookie 或存储事件认证令牌 want="存在认证令牌"

建议操作:

  • 生成认证报告并查看 Login submit 的截图,验证登录是否按预期工作。
  • 使用浏览器的开发者工具,调查登录时创建的 cookies 和本地/会话存储对象。确保存在具有足够随机值的认证令牌。
  • 如果使用 cookies 存储认证令牌,请使用 DAST_AUTH_COOKIE_NAMES 设置认证令牌 cookie 的名称。