`PATCH /phone/auto_receptionists/{id}/ivr` returns 204 but doesn't persist any changes

API Endpoint(s) and/or Zoom API Event(s)


Description

I’m trying to configure the IVR menu on an Auto Receptionist programmatically — set the audio_prompt and define key_actions so that pressing 1, 2, 3, etc. routes the caller to specific users, a call queue, or another Auto Receptionist. Goal is to manage IVR config from code rather than the web admin UI.

The PATCH endpoint accepts the request, returns success, but the changes never persist.


Error?

No error returned. The endpoint returns HTTP 204 with an empty body. A subsequent GET on the same endpoint shows the IVR completely unchanged.

The server is parsing the body — sending an invalid caller_enters_no_action.action value correctly returns:

HTTP 400"The action value set for if caller enters no action after the prompt played is not correct."

So validation runs. It just silently no-ops on payloads that pass validation.


How To Reproduce

  1. Authentication method / app type: Server-to-Server OAuth app, account-credentials grant. Token includes all phone:*:auto_receptionist*:admin scopes (e.g. phone:write:auto_receptionist_ivr:admin, phone:read:auto_receptionist_ivr:admin). Bearer token verified valid by GET calls on the same endpoint returning correct data.

  2. Request — minimal repro:

    PATCH /v2/phone/auto_receptionists/{autoReceptionistId}/ivr?hours_type=business_hours
    Host: api.zoom.us
    Authorization: Bearer <token>
    Content-Type: application/json
    
    

    Body:

    {
      "key_actions": [
        { "key": "1", "action": 2, "target": { "extension_id": "<user-extension-id>" } }
      ]
    }
    
    
  3. Response:

    HTTP/2 204
    (empty body)
    
    
  4. Verification:

    GET /v2/phone/auto_receptionists/{autoReceptionistId}/ivr?hours_type=business_hours
    
    

    Returns the prior state — the new key: "1" entry is not present.

  5. Variants tested, all silently no-op:

    • With and without ?hours_type=business_hours

    • Single-key updates and full-replacement payloads

    • Every documented value of key_actions[].action (1, 2, 3, 4, 6, 7, 21, 100, 200)

    • audio_prompt updates with a valid prompt id from GET /phone/users/me/audios

    • PATCHing through /phone/extension/{extensionId}/call_handling/settings/{settingType} for the same Auto Receptionist’s extension — same silent no-op behavior on AR-related settings

    • Refreshed the OAuth token between attempts

  6. What works for comparison:

    • GET on the same endpoint returns correct data

    • Configuring the identical IVR through the web admin UI at zoom.us works correctly, and the new state is then visible via GET — so the underlying data path is fine, only programmatic writes are dropped

    • The PATCH endpoint does validate input — invalid values return a real 400 with a meaningful message

  7. Sample trace identifiers from no-op PATCH responses (in case they help trace internally):

    • zm-cube-traceid: fec3f9d3e76e740e4750f0ebcf1eb8cd

    • x-zm-trackingid: WEB_5516d382133d6a589a48e7e823a95074

    • Region header: x-zm-region: VA

Has anyone seen this, or is there a known restriction on programmatic IVR writes? If certain Phone tiers don’t support PATCH on this endpoint, returning a 4xx instead of a silent 204 would make the limit much easier to discover.

Thanks.

This is an accidental duplicate post; please delete