> ## Documentation Index
> Fetch the complete documentation index at: https://docs.didit.me/llms.txt
> Use this file to discover all available pages before exploring further.

# 更新功能状态 API：通过或拒绝单个验证步骤

> Didit 允许你通过 API 将单个验证步骤（OCR、活体检测、人脸比对、AML、地址证明、电话验证等）设为已通过、已拒绝或转入人工审核，可立即生效，也可待用户完成流程后再设置。



功能状态更新提示词
        将提示词复制到剪贴板



      
      

\<pre>

\`Approve, decline, or move a SINGLE verification step (feature) of a Didit session to review, now or once the person finishes the flow.

Endpoint:
PATCH https://verification.didit.me/v3/session/{session_id}/features/{node_id}/update-status/

Authentication:
x-api-key (client API key) or a user-auth token. Privilege: write:sessions.

Path parameters:
\- session_id (UUID) — KYC or KYB; Didit resolves it against both session types.
\- node_id — the workflow graph node ID of the step (e.g. feature_ocr_1, feature_liveness_1, feature_aml_1). Use the literal "default" for non-graph (single-step) workflows where the step has no node ID.

Request body:
\- new_status (string, required): one of "Approved", "Declined", "In Review". Must differ from the step's current status.
\- comment (string, optional): your reason, saved in the session's activity and returned as the override's reason.
\- feature_type (string, optional): which kind of step to target, for example "LIVENESS", "AML", "FACE_MATCH", "ID_VERIFICATION". Needed when node_id is "default" (non-graph workflows, where steps have no node ID). An unknown value returns 400 { "feature_type": ["Unknown feature_type '...'."] }.
\- defer_until_flow_finishes (boolean, optional, default false): while the person is still in the flow, wait and apply the override when the flow finishes instead of at once.

When the override applies:
\- Omitted or false: it applies at once. If the person is still in the flow it is recorded as forced=true.
\- true while the person is still in the flow (session Not Started, In Progress or Resubmitted, and not finished): it is stored as "pending_until_flow_finishes" and applies when the flow finishes, after the flow reaches its own decision.
\- true after the flow ended: it applies at once.
\- A waiting override is cancelled instead when the person redoes the step before finishing, a newer override on the same step replaces it, the session leaves the flow unfinished (abandoned, expired, decided mid-flow), or you cancel it with POST /v3/session/{session_id}/features/overrides/{override_id}/cancel/.

Which steps this works on:
Every per-step feature record: OCR/ID, Liveness, Face Match, NFC, AML, Proof of Address (POA), Phone, Email, Database Validation, Questionnaire, and the KYB registry / documents / key-people checks.

Difference vs update-status:
\- update-status changes the OVERALL session decision (Approved/Declined/Resubmitted).
\- THIS endpoint changes ONE step's status. A session that already has a decision keeps it. If the session has no decision yet and its workflow is waiting on exactly this step, applying the override completes the step: the workflow moves on and a status node can set the session decision (and fire status.updated).

Not allowed:
\- Standalone API sessions (session_type = API) return 400.

curl example — approve the ID/OCR step:
curl -X PATCH https://verification.didit.me/v3/session/<SESSION_ID>/features/feature_ocr_1/update-status/ \
-H "x-api-key: <API_KEY>" \
-H "Content-Type: application/json" \
-d '{ "new_status": "Approved", "comment": "Document manually verified" }'

Response: { session_id, node_id, feature_type, new_status, override }.
\- node_id is the step's workflow node, or null for a step without a node ("default" in a non-graph workflow).
\- new_status is the step's stored status: the requested one once the override applied, the unchanged one while it waits.
\- override: { id, node_id, feature_type, feature_model, previous_status, new_status, state ("applied" | "pending_until_flow_finishes" | "cancelled"), forced, reason, requested_by { email, name, type }, requested_at, applied_at, cancelled_at, cancel_reason }.

Side effects:
\- Fires a data.updated webhook when the override applies (at once, or when the flow finishes). Nothing is sent while it waits or when it is cancelled.
\- Records the override in the session's activity as FEATURE_OVERRIDE_PENDING, FEATURE_OVERRIDE_APPLIED or FEATURE_OVERRIDE_CANCELLED, with who made it; the request's entry carries your comment. In the decision's reviews array these entries appear with new_status null, and the request's entry has your reason in comment.

Failure modes:
\- 400: new_status invalid or unchanged, unknown feature_type, or the session is a standalone API session.
\- 401: the scoped API key has expired.
\- 403: missing credentials (a wrong, revoked or expired key gets 401), or the caller lacks write:sessions (a scoped key needs decisions write).
\- 404: session not found, or no feature has the given node_id.

Related: list overrides with GET /v3/session/{session_id}/features/overrides/ (see /sessions-api/list-feature-overrides); cancel a waiting one with POST /v3/session/{session_id}/features/overrides/{override_id}/cancel/ (see /sessions-api/cancel-feature-override).

For end-to-end Didit integration, paste in the full prompt at /integration/integration-prompt.`

\</pre>



      
      

粘贴到

## 本接口的作用一个验证会话由多个独立的**功能**（步骤）组成：ID/OCR、活体检测、人脸比对、AML、地址证明、电话等。
此接口可将其中**一个**步骤的状态设置为 `Approved`、`Declined` 或 `In Review`。若要批准、拒绝或重新开启整个会话，请使用 [update-status](https://docs.didit.me/zh/sessions-api/update-status.md)。
若只想记录单个步骤的决定，例如在您自己的审核流程中将人脸比对步骤标记为 `Declined`，请使用**本**接口。已有决定的会话会保留该决定，只有步骤会发生变化。
如果会话尚无决定，且其工作流正在等待这一步，应用覆盖后该步骤会完成，与正常完成该步骤的效果相同。
工作流随后继续运行，后续步骤执行，状态节点可以设置会话决策并触发 `status.updated` Webhook。## 使用 `node_id` 指定步骤在基于图的工作流中，每个步骤都有一个 `node_id`（例如 `feature_ocr_1`、`feature_liveness_1`、`feature_aml_1`）。您可以在[会话决策](https://docs.didit.me/zh/sessions-api/retrieve-session.md)中找到这些 ID，V3 版决策中的每个功能都带有其 `node_id`。对于**非图（单步骤）工作流**，底层功能没有节点 ID。请将字面值 `default` 作为 `nodeId` 传入以指定该步骤。
由于此类工作流中没有任何步骤具有节点 ID，还需传入 `feature_type`（例如 `LIVENESS`、`AML` 或 `FACE_MATCH`）以说明您指的是哪个步骤。
无法识别的 `feature_type` 会返回 `400`。## 等待用户完成流程默认情况下，覆盖立即生效。
如果用户仍在完成流程，则会修改仍在运行的流程中的某个步骤，此时覆盖会记录为 `forced: true`。设置 `defer_until_flow_finishes: true` 可改为等待。
当会话处于 `Not Started`、`In Progress` 或 `Resubmitted` 状态且用户尚未完成流程时，覆盖会存储为 `pending_until_flow_finishes`。
它会在用户完成流程后、流程自身做出决定之后生效。
对于流程已经结束的会话，无论如何设置，覆盖都会立即生效。等待中的覆盖在以下情况下会被取消，而不是生效：- 用户在完成前重做该步骤（`check_changed`），
- 同一步骤上更新的覆盖取代了它（`replaced`），
- 会话在流程未完成时结束：已放弃、已过期或在流程中途已做出决定（`session_closed`），
- 您通过 [取消功能覆盖](https://docs.didit.me/zh/sessions-api/cancel-feature-override.md) 取消了它（`cancelled_by_reviewer`）。响应中的 `override` 说明了结果：`state` 为 `applied` 或 `pending_until_flow_finishes`，生效后会设置 `applied_at`。
顶层的 `new_status` 是该步骤已存储的状态，因此在覆盖等待期间保持不变。
使用 [列出功能覆盖](https://docs.didit.me/zh/sessions-api/list-feature-overrides.md) 可查看某个会话的所有覆盖，以及用户是否仍在流程中。## KYC 与 KYB 支持对**用户验证（KYC）**和**企业验证（KYB）**会话的处理方式完全相同，Didit 可在这两种会话中解析 `sessionId`。支持的步骤类型包括 ID/OCR、活体检测、人脸比对、NFC、AML、地址证明、电话、邮箱、数据库核验、问卷，以及 KYB 的公司登记、证件和关键人员检查。> [!NOTE]
>
> 通过独立验证 API 创建的会话（`session_type = API`）无法更改单个功能的状态，接口会返回 `400`。## 示例> [tab] 批准一个步骤
>
> ```bash theme={null}
> curl -X PATCH https://verification.didit.me/v3/session/4c5c7f3a-.../features/feature_ocr_1/update-status/ \
>   -H "x-api-key: YOUR_API_KEY" \
>   -H "Content-Type: application/json" \
>   -d '{
>     "new_status": "Approved",
>     "comment": "Document manually verified by compliance"
>   }'
> ```> [tab] 拒绝人脸比对步骤
>
> ```bash theme={null}
> curl -X PATCH https://verification.didit.me/v3/session/4c5c7f3a-.../features/feature_face_match/update-status/ \
>   -H "x-api-key: YOUR_API_KEY" \
>   -H "Content-Type: application/json" \
>   -d '{
>     "new_status": "Declined"
>   }'
> ```> [tab] 单步骤工作流（默认节点）
>
> ```bash theme={null}
> curl -X PATCH https://verification.didit.me/v3/session/4c5c7f3a-.../features/default/update-status/ \
>   -H "x-api-key: YOUR_API_KEY" \
>   -H "Content-Type: application/json" \
>   -d '{
>     "new_status": "In Review",
>     "feature_type": "LIVENESS"
>   }'
> ```> [tab] 等待用户完成流程
>
> ```bash theme={null}
> curl -X PATCH https://verification.didit.me/v3/session/4c5c7f3a-.../features/feature_liveness_1/update-status/ \
>   -H "x-api-key: YOUR_API_KEY" \
>   -H "Content-Type: application/json" \
>   -d '{
>     "new_status": "Approved",
>     "comment": "Liveness retried with a reviewer present",
>     "defer_until_flow_finishes": true
>   }'
> ```## 更新后会发生什么- **Webhook**：覆盖生效时（立即生效或流程结束时）会触发 `data.updated` 事件。等待期间或取消时不发送任何内容。
- **活动**：每次覆盖都会记录在会话的**活动**中，类型为 `FEATURE_OVERRIDE_PENDING`、`FEATURE_OVERRIDE_APPLIED` 或 `FEATURE_OVERRIDE_CANCELLED`，并附带操作者（API 密钥、用户，或等待中的覆盖生效时的系统）。请求对应的记录会将您的 `comment` 作为原因。在[会话决策](https://docs.didit.me/zh/sessions-api/retrieve-session.md)的 `reviews` 数组中，这些记录显示为 `new_status: null`，请求对应的记录在 `comment` 中包含您填写的原因。
- **会话决策**：已有决策的会话会保留该决策。若要更改最终决策，请单独调用 [update-status](https://docs.didit.me/zh/sessions-api/update-status.md)。## 权限需要 `write:sessions` 权限，可使用客户端 API 密钥（`x-api-key`）或用户授权请求头。
限定范围的 API 密钥需要具备决策的写入权限。## 相关内容- [更新会话状态](https://docs.didit.me/zh/sessions-api/update-status.md)：更改会话的整体决策。
- [更新 AML 命中状态](https://docs.didit.me/zh/sessions-api/update-aml-hit-status.md)：审核单个 AML 匹配结果。
- [获取会话](https://docs.didit.me/zh/sessions-api/retrieve-session.md)：获取决策（及每个功能的 `node_id`）。
- [Webhook](https://docs.didit.me/zh/integration/webhooks.md)：订阅 `data.updated`。
- [列出功能覆盖](https://docs.didit.me/zh/sessions-api/list-feature-overrides.md)：查看会话的每项覆盖及其状态。
- [取消功能覆盖](https://docs.didit.me/zh/sessions-api/cancel-feature-override.md)：阻止等待中的覆盖生效。


## OpenAPI

````yaml zh/openapi-25.json PATCH /v3/session/{sessionId}/features/{nodeId}/update-status/
openapi: 3.0.0
info:
  version: 3.0.0
  title: Didit Verification API
  description: 身份证件验证 API。使用 x-api-key 请求头进行身份验证。
servers:
  - url: https://verification.didit.me
security: []
tags: []
paths:
  /v3/session/{sessionId}/features/{nodeId}/update-status/:
    patch:
      tags:
        - Sessions
      summary: 更新单独功能（步骤）状态
      description: >-
        设置会话中单个验证功能（步骤）的状态。通过其工作流图谱的 `nodeId` 指定该功能。在步骤没有节点的非图谱工作流中，请使用
        `default` 并同时传递 `feature_type` 以指明您所指的步骤。


        适用于用户验证（KYC）和企业验证（KYB）会话以及所有步骤类型：ID/OCR、活体检测、人脸比对、NFC、AML、地址证明、电话、邮箱、数据库核验、问卷，以及
        KYB 公司登记/证件/关键人员核查。此 endpoint **不**适用于独立 API 会话（`session_type = API`）。


        `new_status` 必须为 `Approved`、`Declined` 或 `In Review` 之一，且必须与该功能的当前状态不同。


        **覆盖生效的时间。** 若未设置 `defer_until_flow_finishes`（或设为
        `false`），覆盖将立即生效，与以往相同；当用户仍在流程中时，该操作记录为 `forced`。当用户仍在流程中（会话处于 `Not
        Started`、`In Progress` 或 `Resubmitted` 状态且尚未结束）并设置了
        `defer_until_flow_finishes: true` 时，覆盖将存储为
        `pending_until_flow_finishes`，并在流程结束且自行得出决策后生效。对于流程已经结束的会话，无论哪种情况都会立即生效。当用户在完成流程前重新执行该步骤、同一核查有了较新的覆盖将其替换、会话未完成流程便退出（已放弃、已过期或在流程中途得出决策），或者您使用
        `POST /v3/session/{sessionId}/features/overrides/{overrideId}/cancel/`
        取消它时，等待中的覆盖将被取消。使用 `GET /v3/session/{sessionId}/features/overrides/`
        列出会话的覆盖记录。


        **对会话的影响。**
        已经得出决策的会话将保留该决策：仅核查发生变更。当会话尚未得出决策且其工作流正等待此特定步骤时，应用覆盖将完成该步骤：工作流将继续进行，运行后续步骤，并且状态节点可以设置会话决策并触发
        `status.updated`。


        **Webhook 与活动。** `data.updated` Webhook
        会在覆盖生效时（立即生效或流程结束时）触发，在等待期间或被取消时绝不会触发。每次覆盖都会记录在会话的活动中，标记为
        `FEATURE_OVERRIDE_PENDING`、`FEATURE_OVERRIDE_APPLIED` 或
        `FEATURE_OVERRIDE_CANCELLED`，并附带操作者信息；该请求的记录项会包含您的 `comment`。


        使用您的 API 密钥（`x-api-key`）或带有 `write:sessions` 权限的用户授权请求头进行身份验证；限定作用域的 API
        密钥需要对决策具有写入权限。
      operationId: patch_v3_session_update_feature_status
      parameters:
        - in: path
          name: sessionId
          required: true
          description: 验证会话的 UUID。支持用户（KYC）和企业（KYB）会话 ID，服务会跨两种会话类型解析该 ID。
          schema:
            type: string
            format: uuid
            example: 11111111-2222-3333-4444-555555555555
        - in: path
          name: nodeId
          required: true
          description: >-
            要更新的功能的工作流图谱节点 ID（例如 `feature_ocr_1`）。对于功能没有节点 ID
            的非图谱（单步骤）工作流，请使用字面值 `default`。
          schema:
            type: string
            example: feature_ocr_1
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - new_status
              properties:
                new_status:
                  type: string
                  description: 此功能的目标状态。必须与当前值不同。
                  enum:
                    - Approved
                    - Declined
                    - In Review
                  example: Approved
                comment:
                  type: string
                  description: 可选的自由文本备注，记录在此功能变更的会话审核轨迹中。
                  example: Document manually verified by compliance.
                feature_type:
                  type: string
                  enum:
                    - ID_VERIFICATION
                    - OCR
                    - OCR_BACK
                    - NFC
                    - LIVENESS
                    - FACE
                    - AGE_ESTIMATION
                    - AGE_VERIFICATION
                    - FACE_SEARCH
                    - FACE_MATCH
                    - IP_ANALYSIS
                    - AML
                    - PHONE
                    - PHONE_VERIFICATION
                    - EMAIL
                    - EMAIL_VERIFICATION
                    - POA
                    - PROOF_OF_ADDRESS
                    - DATABASE_VALIDATION
                    - DATA_VALIDATION
                    - QUESTIONNAIRE
                    - DOCUMENT_AI
                    - KYB_REGISTRY
                    - KYB_DOCUMENTS
                    - KYB_KEY_PEOPLE
                    - BANK_VERIFICATION
                    - GEOLOCATION
                  description: >-
                    要定位哪种类型的步骤。非图谱工作流中需要提供（`nodeId` =
                    `default`），此时所有步骤不共享节点；其他情况下可选。未知值将返回 `400`。
                  example: LIVENESS
                defer_until_flow_finishes:
                  type: boolean
                  default: false
                  description: >-
                    当当事人仍在流程中时，将覆盖项存储为 `pending_until_flow_finishes`
                    并在流程结束时应用，而不是立即生效。若省略或设为
                    `false`，覆盖项将立即生效。对于流程已结束的会话，无论哪种情况均会立即生效。
                  example: false
            examples:
              Apply Now:
                summary: 立即通过证件验证步骤
                value:
                  new_status: Approved
                  comment: Document manually verified by compliance.
              Wait For The Flow:
                summary: 用户完成流程后通过活体检测步骤
                value:
                  new_status: Approved
                  comment: Liveness retried with a reviewer present.
                  defer_until_flow_finishes: true
              Non-graph Workflow:
                summary: 针对无节点工作流（nodeId = default）的活体检测步骤
                value:
                  new_status: In Review
                  feature_type: LIVENESS
      responses:
        '200':
          description: >-
            覆盖已记录。`new_status` 是已存储的核验状态：覆盖生效后为请求的状态，等待流程完成期间为未更改的状态。`override`
            说明了实际发生的情况。
          content:
            application/json:
              schema:
                type: object
                properties:
                  session_id:
                    type: string
                    format: uuid
                  node_id:
                    type: string
                    nullable: true
                    description: 已更新步骤的工作流节点；对于没有节点的步骤（非图谱工作流中的 `default` 路径），则为 `null`。
                    example: feature_ocr_1
                  feature_type:
                    type: string
                    description: 已更新功能的模型名称（例如 `KYC`、`Face`、`FaceMatch`、`AML`、`POA`）。
                    example: KYC
                  new_status:
                    type: string
                    description: 该检查的已存储状态：覆盖生效后为所请求的状态，在覆盖等待流程完成期间为未更改的状态。
                    example: Approved
                  override:
                    $ref: '#/components/schemas/FeatureStatusOverride'
                required:
                  - session_id
                  - node_id
                  - feature_type
                  - new_status
                  - override
              examples:
                Applied:
                  summary: 覆盖操作已立即应用
                  value:
                    session_id: 3fa85f64-5717-4562-b3fc-2c963f66afa6
                    node_id: feature_ocr_1
                    feature_type: KYC
                    new_status: Approved
                    override:
                      id: 7c9e6679-7425-40de-944b-e07fc1f90ae7
                      node_id: feature_ocr_1
                      feature_type: ''
                      feature_model: KYC
                      previous_status: In Review
                      new_status: Approved
                      state: applied
                      forced: false
                      reason: Document manually verified by compliance.
                      requested_by:
                        email: reviewer@example.com
                        name: Alex Reviewer
                        type: CONSOLE_USER
                      requested_at: '2026-10-13T09:15:00Z'
                      applied_at: '2026-10-13T09:15:00Z'
                      cancelled_at: null
                      cancel_reason: null
                Waiting For The Flow:
                  summary: 该人员仍在流程中时的 defer_until_flow_finishes
                  value:
                    session_id: 3fa85f64-5717-4562-b3fc-2c963f66afa6
                    node_id: feature_liveness_1
                    feature_type: Face
                    new_status: Declined
                    override:
                      id: 9b2f4c1e-8d3a-4e5f-a6b7-c8d9e0f1a2b3
                      node_id: feature_liveness_1
                      feature_type: ''
                      feature_model: Face
                      previous_status: Declined
                      new_status: Approved
                      state: pending_until_flow_finishes
                      forced: false
                      reason: Liveness retried with a reviewer present.
                      requested_by:
                        email: reviewer@example.com
                        name: Alex Reviewer
                        type: CONSOLE_USER
                      requested_at: '2026-10-13T09:15:00Z'
                      applied_at: null
                      cancelled_at: null
                      cancel_reason: null
        '400':
          description: 验证错误。当 `new_status` 无效或未发生变化、`feature_type` 未知，或者会话为独立 API 会话时返回。
          content:
            application/json:
              examples:
                Same Status:
                  summary: new_status 与当前状态相同
                  value:
                    new_status:
                      - The new status is the same as the current status.
                API Session:
                  summary: 独立 API 会话上的功能状态无法更改
                  value:
                    - Cannot change feature status for API sessions.
                Unknown feature_type:
                  summary: feature_type 不是已知的步骤类型
                  value:
                    feature_type:
                      - Unknown feature_type 'SELFIE'.
        '401':
          description: 作用域 API 密钥已过期。
          content:
            application/json:
              examples:
                Expired API Key:
                  summary: 已过有效期的作用域 API 密钥
                  value:
                    detail: This API key has expired.
        '403':
          description: 缺少凭据或权限不足。
          content:
            application/json:
              examples:
                Invalid Credentials:
                  summary: x-api-key 缺失或无效
                  value:
                    detail: >-
                      Authentication credentials were not provided or are
                      invalid.
                Missing Privilege:
                  summary: API 密钥缺少 write:sessions
                  value:
                    detail: You do not have permission to perform this action.
                Scoped Key Without Access:
                  summary: 没有决策写入权限的作用域 API 密钥
                  value:
                    detail: This API key has no write access to decisions.
        '404':
          description: 未找到该会话，或者该会话没有具有给定 `nodeId` 的功能。
          content:
            application/json:
              examples:
                Session Not Found:
                  summary: 未知的 session_id
                  value:
                    detail: Session not found.
                Feature Not Found:
                  summary: 此 node_id 没有对应功能
                  value:
                    detail: >-
                      No feature found with node_id 'feature_ocr_1' in this
                      session.
      security:
        - ApiKeyAuth: []
      x-codeSamples:
        - lang: curl
          label: curl
          source: |-
            curl -X PATCH \
              https://verification.didit.me/v3/session/11111111-2222-3333-4444-555555555555/features/feature_ocr_1/update-status/ \
              -H 'x-api-key: YOUR_API_KEY' \
              -H 'Content-Type: application/json' \
              -d '{
                "new_status": "Approved",
                "comment": "Document manually verified by compliance."
              }'
        - lang: python
          label: Python
          source: |-
            from didit import Didit

            # Reads DIDIT_API_KEY.
            client = Didit()

            result = client.sessions.update_feature_status(
                "11111111-2222-3333-4444-555555555555",
                "feature_ocr_1",
                new_status="Approved",
                comment="Document manually verified by compliance.",
            )
            print(result)
        - lang: javascript
          label: Node.js
          source: |-
            import Didit from "@didit-protocol/sdk-node";

            // Reads DIDIT_API_KEY.
            const didit = new Didit();

            const result = await didit.sessions.updateFeatureStatus(
              "11111111-2222-3333-4444-555555555555",
              "feature_ocr_1",
              {
                new_status: "Approved",
                comment: "Document manually verified by compliance.",
              },
            );
            console.log(result);
        - lang: go
          label: Go
          source: "ctx := context.Background()\n// Reads DIDIT_API_KEY.\nclient := didit.NewClient()\n\nresult, err := client.Sessions.UpdateFeatureStatus(ctx, \"11111111-2222-3333-4444-555555555555\", \"feature_ocr_1\", didit.SessionsUpdateFeatureStatusParams{\n\tNewStatus: \"Approved\",\n\tComment:   didit.String(\"Document manually verified by compliance.\"),\n})\nif err != nil {\n\tlog.Fatal(err)\n}\nfmt.Printf(\"%+v\\n\", result)"
        - lang: java
          label: Java
          source: >-
            import me.didit.Didit;

            import me.didit.types.SessionsUpdateFeatureStatusParams;


            // Reads DIDIT_API_KEY.

            Didit client = new Didit();


            var result =
            client.sessions().updateFeatureStatus("11111111-2222-3333-4444-555555555555",
            "feature_ocr_1", SessionsUpdateFeatureStatusParams.builder()
                    .newStatus(SessionsUpdateFeatureStatusParams.NewStatus.of("Approved"))
                    .comment("Document manually verified by compliance.")
                    .build());
            System.out.println(result);
        - lang: php
          label: PHP
          source: >-
            <?php


            require 'vendor/autoload.php';


            use Didit\DiditClient;


            // Reads DIDIT_API_KEY.

            $didit = new DiditClient();


            $result =
            $didit->sessions->updateFeatureStatus('11111111-2222-3333-4444-555555555555',
            'feature_ocr_1', [
                'new_status' => 'Approved',
                'comment' => 'Document manually verified by compliance.',
            ]);

            print_r($result->toArray());
        - lang: ruby
          label: Ruby
          source: |-
            require "didit"

            # Reads DIDIT_API_KEY.
            didit = Didit::Client.new

            result = didit.sessions.update_feature_status(
              "11111111-2222-3333-4444-555555555555",
              "feature_ocr_1",
              new_status: "Approved",
              comment: "Document manually verified by compliance."
            )
            puts result.to_h
        - lang: csharp
          label: .NET
          source: >-
            using System;

            using System.Text.Json;

            using Didit;


            // Reads DIDIT_API_KEY.

            using var client = new DiditClient();


            var result = await
            client.Sessions.UpdateFeatureStatusAsync("11111111-2222-3333-4444-555555555555",
            "feature_ocr_1", new SessionsUpdateFeatureStatusParams

            {
                NewStatus = "Approved",
                Comment = "Document manually verified by compliance.",
            });

            Console.WriteLine(JsonSerializer.Serialize(result));
components:
  schemas:
    FeatureStatusOverride:
      type: object
      description: >-
        通过 `PATCH /v3/session/{sessionId}/features/{nodeId}/update-status/`
        对某项检查（功能）状态进行的一次覆盖：它更改了什么、是否已应用或仍在等待用户完成流程、发起者以及原因。
      required:
        - id
        - node_id
        - feature_type
        - feature_model
        - previous_status
        - new_status
        - state
        - forced
        - reason
        - requested_by
        - requested_at
        - applied_at
        - cancelled_at
        - cancel_reason
      properties:
        id:
          type: string
          format: uuid
          description: 覆盖项的标识符。将其传递给取消 endpoint。
          example: 7c9e6679-7425-40de-944b-e07fc1f90ae7
        node_id:
          type: string
          description: 请求指定的工作流节点（对于没有节点的步骤为 `default`）。
          example: feature_ocr_1
        feature_type:
          type: string
          description: 请求传递的 `feature_type`；若未传递，则为空字符串。
          example: ''
        feature_model:
          type: string
          description: 被覆盖的核验类型，例如 `KYC`、`Face`、`AML` 或 `GeolocationCheck`。
          example: KYC
        previous_status:
          type: string
          enum:
            - Not Finished
            - Approved
            - Declined
            - In Review
            - Resub Requested
          description: 请求覆盖时该检查的状态。
          example: In Review
        new_status:
          type: string
          enum:
            - Approved
            - Declined
            - In Review
          description: 覆盖所设置的状态。
          example: Approved
        state:
          type: string
          enum:
            - applied
            - pending_until_flow_finishes
            - cancelled
          description: >-
            `applied`：检查已获得新状态。`pending_until_flow_finishes`：覆盖设置处于等待状态，并在该人员完成流程时应用。`cancelled`：已等待且从未应用（参见
            `cancel_reason`）。
          example: applied
        forced:
          type: boolean
          description: 当该人员仍在流程中且覆写立即生效时为 `true`。
          example: false
        reason:
          type: string
          nullable: true
          description: 随请求发送的 `comment`，或为 `null`。
          example: Document manually verified by compliance.
        requested_by:
          type: object
          nullable: true
          description: 请求覆盖的人员；若未知则为 `null`。
          properties:
            email:
              type: string
              format: email
              nullable: true
              description: Console 用户的邮箱，对于 API 密钥和系统则为 `null`。
              example: reviewer@example.com
            name:
              type: string
              nullable: true
              description: 请求者的显示名称，或 `null`。
              example: Alex Reviewer
            type:
              type: string
              enum:
                - CONSOLE_USER
                - API_KEY
                - SYSTEM
              description: 发起请求的主体：控制台用户、API 密钥或 Didit 本身。
              example: CONSOLE_USER
        requested_at:
          type: string
          format: date-time
          description: 请求覆盖的时间。
          example: '2026-10-13T09:15:00Z'
        applied_at:
          type: string
          format: date-time
          nullable: true
          description: 检查变为新状态的时间，等待中或一旦取消则为 `null`。
          example: '2026-10-13T09:15:00Z'
        cancelled_at:
          type: string
          format: date-time
          nullable: true
          description: 等待中的覆盖被取消的时间，或为 `null`。
          example: null
        cancel_reason:
          type: string
          nullable: true
          enum:
            - cancelled_by_reviewer
            - replaced
            - check_changed
            - session_closed
            - null
          description: >-
            处于等待状态的覆盖为何从未生效，或为 `null`。`cancelled_by_reviewer`：已通过取消 endpoint
            取消。`replaced`：同一项检查上更新的覆盖替换了它。`check_changed`：用户在完成流程之前重新进行了检查。`session_closed`：会话在用户完成之前离开了流程（已放弃、已过期或在流程中做出决策）。
          example: null
  securitySchemes:
    ApiKeyAuth:
      type: apiKey
      in: header
      name: x-api-key
      description: >-
        您的应用 API 密钥，可在 Business Console 的“开发者 -> API
        密钥”中获取。主密钥拥有完整访问权限。指定名称的密钥可设置作用域：针对每个资源设为无权限、只读或读写，限定于特定工作流或已通过的会话、限定于
        IP 地址列表，以及设置到期日期。401 表示密钥错误、已撤销或已过期；403 表示未发送密钥、密钥无权访问该资源或操作，或请求来自其 IP
        列表之外的地址；在会话路由上返回 404 表示该会话不在该密钥允许的工作流或状态范围内。没有媒体访问权限的密钥获取到的图片、视频和 PDF
        URL 将为 null；没有会话写入权限的密钥获取到的会话链接和 token 将为 null。请参阅
        https://docs.didit.me/console/api-keys。

````

This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.