Something is weird with the behavior of the PATCH /api/v2/users/{userId}/skills endpoint. I’m trying to automate the bulk update of agent skill proficiencies based on a nightly CSV feed from our WFM system. The goal is to set the proficiency level for specific skills without overwriting other existing skills.
Here is the setup:
- Endpoint:
PATCH /api/v2/users/{userId}/skills - Auth: OAuth2 Client Credentials with
admin:skill:writescope. - Payload: A list of skill objects with
idandproficiency.
The first run of the script works fine. It updates the proficiencies for 50 agents. I run it again an hour later with the same data (no changes in the CSV), and suddenly I get a 409 Conflict for about 10% of the users.
The error payload looks like this:
{
"code": "duplicate",
"message": "Skill assignment already exists for user."
}
I checked the documentation. It says PATCH should be idempotent or at least handle existing assignments gracefully by updating the value. It shouldn’t throw a conflict if the skill is already assigned, especially if I’m just updating the proficiency level.
I’ve tried the following:
- Verifying the
proficiencyvalue is an integer (1-5) as expected. - Checking if the skill
idis correct. It matches the skill ID returned by the search API. - Adding a delay between requests to avoid rate limiting, though the error is 409, not 429.
- Using
PUTinstead ofPATCH. This fails with a400 Bad Requestsaying the request body is invalid, which makes sense becausePUTusually expects the full list of skills, and I only want to update specific ones.
Is this a known bug with the Admin API? Or am I missing a header or query parameter that tells the API to “update if exists”? The script is written in Python using the requests library. The code is standard:
headers = {
'Authorization': f'Bearer {token}',
'Content-Type': 'application/json'
}
data = [{"id": skill_id, "proficiency": level}]
response = requests.patch(f'https://{org_id}.mypurecloud.com/api/v2/users/{user_id}/skills', headers=headers, json=data)
The weird part is that it works for some users and fails for others in the same batch. The users who fail are not special in any way. They are all active agents with the same role.