---
title: Patch
description: Examples in this documentation depend on features activated in the ds-evaluation setup profile.
component: pingds
version: 8.1
page_id: pingds:rest-guide:patch-rest
canonical_url: https://docs.pingidentity.com/pingds/8.1/rest-guide/patch-rest.html
revdate: 2025-10-22T14:42:39Z
keywords: ["REST API"]
section_ids:
  add_a_member_to_a_group: Add a member to a group
  remove_a_member_from_a_group: Remove a member from a group
  add_multiple_values: Add multiple values
  patch_a_specific_revision: Patch a specific revision
---

# Patch

|   |                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                           |
| - | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|   | Examples in this documentation depend on features activated in [the `ds-evaluation` setup profile](../install-guide/setup-ds.html#about-ds-evaluation).The code samples demonstrate how to contact the server over HTTPS using the deployment CA certificate. Before trying the samples, generate the CA certificate in PEM format from the server deployment ID and password:```console
$ dskeymgr \
 export-ca-cert \
 --deploymentId $DEPLOYMENT_ID \
 --deploymentIdPassword password \
 --outputFile ca-cert.pem
``` |

The [patch operation](rest-operations.html#patch) updates one or more fields of a resource. Use it when you must make fine-grained changes to a resource; for example:

* Add a member to a static group.

* Remove a member from a static group.

* Add or remove a single mail address or telephone number.

If you intend only to *replace* fields' values, update the resource instead with HTTP PUT and a partial resource including just the fields to replace.

## Add a member to a group

The following example adds Babs to a static group:

* Curl

* JavaScript

* Python

* Ruby

```console
$ curl \
 --request PATCH \
 --cacert ca-cert.pem \
 --user dc=com/dc=example/ou=People/uid=kvaughan:bribery \
 --header 'Content-Type: application/json' \
 --data '[{
  "operation": "add",
  "field": "uniqueMember",
  "value": "dc=com/dc=example/ou=People/uid=bjensen"
  }]' \
 'https://localhost:8443/hdap/dc=com/dc=example/ou=Groups/cn=Directory%20Administrators?_prettyPrint=true'
```

> **Collapse: Show output**
>
> ```
> {
>   "_id" : "dc=com/dc=example/ou=Groups/cn=Directory%20Administrators",
>   "objectClass" : [ "groupofuniquenames", "top" ],
>   "cn" : [ "Directory Administrators" ],
>   "ou" : [ "Groups" ],
>   "uniqueMember" : [ "dc=com/dc=example/ou=People/uid=kvaughan", "dc=com/dc=example/ou=People/uid=rdaugherty", "dc=com/dc=example/ou=People/uid=hmiller", "dc=com/dc=example/ou=People/uid=bjensen" ]
> }
> ```

```javascript
(async () => {
    const { authenticate, doRequest, getOptions } = require('./utils')
    const options = getOptions({
        path: '/hdap/dc=com/dc=example/ou=Groups/cn=Directory%20Administrators',
        method: 'PATCH',
        body: [{
            "operation": "add",
            "field": "uniqueMember",
            "value": "dc=com/dc=example/ou=People/uid=bjensen"
        }]
    })
    const jwt = await authenticate(options)
    options.headers['Authorization'] = 'Bearer ' + jwt
    const response = await doRequest('HDAP: add group member', options)
    console.log(response)
})().catch(error => { console.error(error) })
```

Source files for this sample: [patch-group-add.js](../_attachments/hdap/js/patch-group-add.js), [utils.js](../_attachments/hdap/js/utils.js)

```python
#!/usr/bin/env python3

import requests
import utils

patch = [{
    'operation': 'add',
    'field': 'uniqueMember',
    'value': 'dc=com/dc=example/ou=People/uid=bjensen'
}]
jwt = utils.authenticate('dc=com/dc=example/ou=People/uid=kvaughan', 'bribery')
headers = { 'Content-Type': 'application/json', 'Authorization': f'Bearer {jwt}' }
response = requests.patch(
    f'https://{utils.host}:{utils.port}/hdap/dc=com/dc=example/ou=Groups/cn=Directory%20Administrators',
    headers=headers,
    json=patch,
    verify=utils.ca_pem)
print('Status code: %d\nJSON: %s' % (response.status_code, response.json()))
```

Source files for this sample: [utils.py](../_attachments/hdap/py/utils.py), [patch-group-add.py](../_attachments/hdap/py/patch-group-add.py)

```ruby
require_relative 'utils.rb'
require 'faraday'
require 'json'

utils = Utils.new('dc=com/dc=example/ou=People/uid=kvaughan', 'bribery')
options = { ca_file: utils.ca_pem }
jwt = utils.authenticate
hdap = Faraday.new(url: "https://#{utils.host}:#{utils.port}/hdap/", ssl: options) do |f|
    f.headers['Content-Type'] = 'application/json'
    f.request :authorization, 'Bearer', jwt
end
patch = [{
    "operation" => "add",
    "field" => "uniqueMember",
    "value" => "dc=com/dc=example/ou=People/uid=bjensen"
}]
response = hdap.patch do |h|
    h.path = 'dc=com/dc=example/ou=Groups/cn=Directory%20Administrators'
    h.body = JSON.generate(patch)
end

puts "Status code: #{response.status}\nJSON: #{response.body}"
```

Source files for this sample: [utils.rb](../_attachments/hdap/rb/utils.rb), [patch-group-add.rb](../_attachments/hdap/rb/patch-group-add.rb)

HDAP Ruby examples require Ruby 3.2 and the `faraday` and `json` gems.

## Remove a member from a group

The following example removes Babs from the group:

* Curl

* JavaScript

* Python

* Ruby

```console
$ curl \
 --request PATCH \
 --cacert ca-cert.pem \
 --user dc=com/dc=example/ou=People/uid=kvaughan:bribery \
 --header 'Content-Type: application/json' \
 --data '[{
  "operation": "remove",
  "field": "uniqueMember",
  "value": "dc=com/dc=example/ou=People/uid=bjensen"
  }]' \
 'https://localhost:8443/hdap/dc=com/dc=example/ou=Groups/cn=Directory%20Administrators?_prettyPrint=true'
```

> **Collapse: Show output**
>
> ```
> {
>   "_id" : "dc=com/dc=example/ou=Groups/cn=Directory%20Administrators",
>   "objectClass" : [ "groupofuniquenames", "top" ],
>   "cn" : [ "Directory Administrators" ],
>   "ou" : [ "Groups" ],
>   "uniqueMember" : [ "dc=com/dc=example/ou=People/uid=kvaughan", "dc=com/dc=example/ou=People/uid=rdaugherty", "dc=com/dc=example/ou=People/uid=hmiller" ]
> }
> ```

```javascript
(async () => {
    const { authenticate, doRequest, getOptions } = require('./utils')
    const options = getOptions({
        path: '/hdap/dc=com/dc=example/ou=Groups/cn=Directory%20Administrators',
        method: 'PATCH',
        body: [{
            "operation": "remove",
            "field": "uniqueMember",
            "value": "dc=com/dc=example/ou=People/uid=bjensen"
        }]
    })
    const jwt = await authenticate(options)
    options.headers['Authorization'] = 'Bearer ' + jwt
    const response = await doRequest('HDAP: remove group member', options)
    console.log(response)
})().catch(error => { console.error(error) })
```

Source files for this sample: [patch-group-remove.js](../_attachments/hdap/js/patch-group-remove.js), [utils.js](../_attachments/hdap/js/utils.js)

```python
#!/usr/bin/env python3

import requests
import utils

patch = [{
    'operation': 'remove',
    'field': 'uniqueMember',
    'value': 'dc=com/dc=example/ou=People/uid=bjensen'
}]
jwt = utils.authenticate('dc=com/dc=example/ou=People/uid=kvaughan', 'bribery')
headers = { 'Content-Type': 'application/json', 'Authorization': f'Bearer {jwt}' }
response = requests.patch(
    f'https://{utils.host}:{utils.port}/hdap/dc=com/dc=example/ou=Groups/cn=Directory%20Administrators',
    headers=headers,
    json=patch,
    verify=utils.ca_pem)
print('Status code: %d\nJSON: %s' % (response.status_code, response.json()))
```

Source files for this sample: [utils.py](../_attachments/hdap/py/utils.py), [patch-group-remove.py](../_attachments/hdap/py/patch-group-remove.py)

```ruby
require_relative 'utils.rb'
require 'faraday'
require 'json'

utils = Utils.new('dc=com/dc=example/ou=People/uid=kvaughan', 'bribery')
options = { ca_file: utils.ca_pem }
jwt = utils.authenticate
hdap = Faraday.new(url: "https://#{utils.host}:#{utils.port}/hdap/", ssl: options) do |f|
    f.headers['Content-Type'] = 'application/json'
    f.request :authorization, 'Bearer', jwt
end
patch = [{
    "operation" => "remove",
    "field" => "uniqueMember",
    "value" => "dc=com/dc=example/ou=People/uid=bjensen"
}]
response = hdap.patch do |h|
    h.path = 'dc=com/dc=example/ou=Groups/cn=Directory%20Administrators'
    h.body = JSON.generate(patch)
end

puts "Status code: #{response.status}\nJSON: #{response.body}"
```

Source files for this sample: [utils.rb](../_attachments/hdap/rb/utils.rb), [patch-group-remove.rb](../_attachments/hdap/rb/patch-group-remove.rb)

HDAP Ruby examples require Ruby 3.2 and the `faraday` and `json` gems.

## Add multiple values

To change multiple fields, include multiple operation objects in the patch payload:

* Curl

* JavaScript

* Python

* Ruby

```console
$ curl \
 --request PATCH \
 --cacert ca-cert.pem \
 --user dc=com/dc=example/ou=People/uid=kvaughan:bribery \
 --header 'Content-Type: application/json' \
 --data '[{
  "operation": "add",
  "field": "telephoneNumber",
  "value": "+1 408 555 9999"
 }, {
  "operation": "add",
  "field": "mail",
  "value": "barbara.jensen@example.com"
 }]' \
 'https://localhost:8443/hdap/dc=com/dc=example/ou=People/uid=bjensen?_fields=mail,telephoneNumber&_prettyPrint=true'
```

> **Collapse: Show output**
>
> ```
> {
>   "_id" : "dc=com/dc=example/ou=People/uid=bjensen",
>   "telephoneNumber" : [ "+1 408 555 1862", "+1 408 555 9999" ],
>   "mail" : [ "bjensen@example.com", "barbara.jensen@example.com" ]
> }
> ```

```javascript
(async () => {
    const { authenticate, doRequest, getOptions } = require('./utils')
    const options = getOptions({
        path: '/hdap/dc=com/dc=example/ou=People/uid=bjensen?_fields=mail,telephoneNumber',
        method: 'PATCH',
        body: [{
            "operation": "add",
            "field": "telephoneNumber",
            "value": "+1 408 555 9999"
        }, {
            "operation": "add",
            "field": "mail",
            "value": "barbara.jensen@example.com"
        }]
    })
    const jwt = await authenticate(options)
    options.headers['Authorization'] = 'Bearer ' + jwt
    const response = await doRequest('HDAP: patch multiple fields', options)
    console.log(response)
})().catch(error => { console.error(error) })
```

Source files for this sample: [patch-multiple.js](../_attachments/hdap/js/patch-multiple.js), [utils.js](../_attachments/hdap/js/utils.js)

```python
#!/usr/bin/env python3

import requests
import utils

patch = [{
    'operation': 'add',
    'field': 'telephoneNumber',
    'value': '+1 408 555 9999'
}, {
    'operation': 'add',
    'field': 'mail',
    'value': 'barbara.jensen@example.com'
}]
jwt = utils.authenticate('dc=com/dc=example/ou=People/uid=kvaughan', 'bribery')
headers = { 'Content-Type': 'application/json', 'Authorization': f'Bearer {jwt}' }
params = { '_fields': 'mail,telephoneNumber' }
response = requests.patch(
    f'https://{utils.host}:{utils.port}/hdap/dc=com/dc=example/ou=People/uid=bjensen',
    headers=headers,
    json=patch,
    params=params,
    verify=utils.ca_pem)
print('Status code: %d\nJSON: %s' % (response.status_code, response.json()))
```

Source files for this sample: [utils.py](../_attachments/hdap/py/utils.py), [patch-multiple.py](../_attachments/hdap/py/patch-multiple.py)

```ruby
require_relative 'utils.rb'
require 'faraday'
require 'json'

utils = Utils.new('dc=com/dc=example/ou=People/uid=kvaughan', 'bribery')
options = { ca_file: utils.ca_pem }
jwt = utils.authenticate
fields = { '_fields': 'mail,telephoneNumber' }
hdap = Faraday.new(url: "https://#{utils.host}:#{utils.port}/hdap/", params: fields, ssl: options) do |f|
    f.headers['Content-Type'] = 'application/json'
    f.request :authorization, 'Bearer', jwt
end
patch = [{
    "operation" => "add",
    "field" => "telephoneNumber",
    "value" => "+1 408 555 9999"
}, {
    "operation" => "add",
    "field" => "mail",
    "value" => "barbara.jensen@example.com"
}]
response = hdap.patch do |h|
    h.path = 'dc=com/dc=example/ou=People/uid=bjensen'
    h.body = JSON.generate(patch)
end

puts "Status code: #{response.status}\nJSON: #{response.body}"
```

Source files for this sample: [utils.rb](../_attachments/hdap/rb/utils.rb), [patch-multiple.rb](../_attachments/hdap/rb/patch-multiple.rb)

HDAP Ruby examples require Ruby 3.2 and the `faraday` and `json` gems.

For a multivalued attribute, the `value` field takes an array. whereas the `value` field takes a single value for a single-valued field. For single-valued fields, an `add` operation has the same effect as a `replace` operation.

## Patch a specific revision

Use an `If-Match: <revision>` header to patch only a specific revision of a resource:

* Curl

* JavaScript

* Python

* Ruby

```console
$ export JWT=$(echo $(curl \
 --request POST \
 --cacert ca-cert.pem \
 --header 'Content-Type: application/json' \
 --data '{ "password": "bribery" }' \
 --silent \
 'https://localhost:8443/hdap/dc=com/dc=example/ou=People/uid=kvaughan?_action=authenticate') | jq -r .access_token)
$ export REVISION=$(cut -d \" -f 8 <(curl \
 --get \
 --cacert ca-cert.pem \
 --header "Authorization: Bearer $JWT" \
 --header 'Content-Type: application/json' \
 --data '_fields=_rev' \
 --silent \
'https://localhost:8443/hdap/dc=com/dc=example/ou=People/uid=bjensen'))
$ curl \
 --request PATCH \
 --cacert ca-cert.pem \
 --header "Authorization: Bearer $JWT" \
 --header 'Content-Type: application/json' \
 --header "If-Match: $REVISION" \
 --data '[{
  "operation": "remove",
  "field": "telephoneNumber",
  "value": "+1 408 555 9999"
 }, {
  "operation": "remove",
  "field": "mail",
  "value": "barbara.jensen@example.com"
 }]' \
 'https://localhost:8443/hdap/dc=com/dc=example/ou=People/uid=bjensen?_fields=mail,telephoneNumber&_prettyPrint=true'
```

> **Collapse: Show output**
>
> ```
> {
>   "_id" : "dc=com/dc=example/ou=People/uid=bjensen",
>   "telephoneNumber" : [ "+1 408 555 1862" ],
>   "mail" : [ "bjensen@example.com" ]
> }
> ```

```javascript
(async () => {
    const { authenticate, doRequest, getOptions } = require('./utils')
    const options = getOptions({
        path: '/hdap/dc=com/dc=example/ou=People/uid=bjensen',
        body: [{
            "operation": "add",
            "field": "telephoneNumber",
            "value": "+1 408 555 9999"
        }, {
            "operation": "add",
            "field": "mail",
            "value": "barbara.jensen@example.com"
        }]
    })
    const jwt = await authenticate(options)
    options.headers['Authorization'] = 'Bearer ' + jwt
    let response = await doRequest('HDAP: read bjensen _rev', options)
    console.log(response)
    options.headers['If-Match'] = JSON.parse(response.data)._rev
    options.method = 'PATCH'
    response = await doRequest('HDAP: patch specific revision', options)
    console.log(response)
})().catch(error => { console.error(error) })
```

Source files for this sample: [patch-rev.js](../_attachments/hdap/js/patch-rev.js), [utils.js](../_attachments/hdap/js/utils.js)

```python
#!/usr/bin/env python3

import requests
import utils

jwt = utils.authenticate('dc=com/dc=example/ou=People/uid=kvaughan', 'bribery')
headers = { 'Content-Type': 'application/json', 'Authorization': f'Bearer {jwt}' }
rev = requests.get(f'https://{utils.host}:{utils.port}/hdap/dc=com/dc=example/ou=People/uid=bjensen',
    headers=headers,
    verify=utils.ca_pem).json()['_rev']

headers['If-Match'] = rev
patch = [{
    'operation': 'add',
    'field': 'telephoneNumber',
    'value': '+1 408 555 9999'
}, {
    'operation': 'add',
    'field': 'mail',
    'value': 'barbara.jensen@example.com'
}]
params = { '_fields': 'mail,telephoneNumber' }
response = requests.patch(
    f'https://{utils.host}:{utils.port}/hdap/dc=com/dc=example/ou=People/uid=bjensen',
    headers=headers,
    json=patch,
    params=params,
    verify=utils.ca_pem)
print('Status code: %d\nJSON: %s' % (response.status_code, response.json()))
```

Source files for this sample: [utils.py](../_attachments/hdap/py/utils.py), [patch-rev.py](../_attachments/hdap/py/patch-rev.py)

```ruby
require_relative 'utils.rb'
require 'faraday'
require 'json'

utils = Utils.new('dc=com/dc=example/ou=People/uid=kvaughan', 'bribery')
options = { ca_file: utils.ca_pem }
jwt = utils.authenticate
fields = { '_fields': 'mail,telephoneNumber' }
hdap = Faraday.new(url: "https://#{utils.host}:#{utils.port}/hdap/", params: fields, ssl: options) do |f|
    f.headers['Content-Type'] = 'application/json'
    f.request :authorization, 'Bearer', jwt
end
patch = [{
    "operation" => "add",
    "field" => "telephoneNumber",
    "value" => "+1 408 555 9999"
}, {
    "operation" => "add",
    "field" => "mail",
    "value" => "barbara.jensen@example.com"
}]
resource = 'dc=com/dc=example/ou=People/uid=bjensen'
rev = JSON.parse(hdap.get(resource).body, symbolize_names: true)[:_rev]

response = hdap.patch do |h|
    h.path = resource
    h.body = JSON.generate(patch)
    h.headers['If-Match'] = rev
end

puts "Status code: #{response.status}\nJSON: #{response.body}"
```

Source files for this sample: [utils.rb](../_attachments/hdap/rb/utils.rb), [patch-rev.rb](../_attachments/hdap/rb/patch-rev.rb)

HDAP Ruby examples require Ruby 3.2 and the `faraday` and `json` gems.

The resource revision changes when the patch is successful.
