Save a contact
Does what Add to contacts and Keep in contacts do in the app, and is safe whatever state the address is in. An address that is not a contact yet becomes one, answered with `201`. One recorded from a send becomes `manual`, and one already saved keeps what it has, answered with `200`. A deleted address is brought back. The body is optional.
Runs the real call against your workspace, with your own key.
PUT /contacts/{email}
Does what Add to contacts and Keep in contacts do in the app, and is safe whatever state the address is in. An address that is not a contact yet becomes one, answered with 201. One recorded from a send becomes manual, and one already saved keeps what it has, answered with 200. A deleted address is brought back. The body is optional.
Example
Needs contacts:write. URL-encode the @.
curl -X PUT "$OE/contacts/grace%40example.com" -H "$AUTH" -H 'content-type: application/json' -d '{ "name": "Grace Hopper"}'{ "object": "contact", "email": "[email protected]", "name": "Grace Hopper", "source": "manual", "notes": null, "photoUrl": null, "lastSeenAt": "2026-09-20T12:00:00.000Z", "createdAt": "2026-09-02T08:00:00.000Z", "updatedAt": "2026-09-23T10:15:00.000Z", "audiences": [ { "id": "aud_9f2c4b7e1a0d63d84c5f2e7b", "name": "All contacts", "builtin": "default" } ]}name replaces the stored name and leaving it out keeps it. notes replaces the stored notes and null clears them. Any other key is a 422 unknown_parameter.
Unlike POST /contacts, an address already in the book is not a 409; unlike PATCH, an address not in the book is not a 404. A new contact joins the default audience.