# Contact Management



Overview [#overview]

Socotra allows you to define contacts that can be managed in association with a variety of entities:

* Accounts
* Policies
* Quotes and Quick Quotes
* FNOLs

Configuring Contacts [#configuring-contacts]

You define contacts at the <ApiLink name="ConfigurationRef">top level of your configuration</ApiLink>, associating a `contacts` property with a map of key-value pairs, where the key is the Pascal-cased contact type name and the value is a `ContactRef`:

<ApiSchema name="ContactRef" />

You must also define contact roles, which provide more context around how various contact types should be associated with a given entity. To define these, simply list them in an array assigned to the top-level `contactRoles` property.

See the [contacts tutorial](#contacts-tutorial) below for details on practical use.

Contact States [#contact-states]

Contacts may be in `draft`, `validated`, or `discarded` state. Contacts first enter the `draft` state on creation and can be explicitly validated, or set with `autoValidate` on creation. Versioning history is only kept for `validated` contacts.

Contacts may be `discarded` by the [merge feature](#merging-contacts).

<Callout>
  Customized contact validation will be enabled in a future plugin.
</Callout>

<span id="contacts-tutorial" />

Tutorial [#tutorial]

Suppose you would like to have an agent optionally associated with every account. You could start by defining a "Person" contact in your top-level configuration like the following, and declare "agent" as one of the recognized `contactRoles`:

```javascript
{
    // ...,
    contacts: {
        "Person": {
            "data": {
                "firstName": {
                    "type": "string"
                },
                "lastName": {
                    "type": "string"
                }
            }
        }
    },
    contactRoles: ["agent"]
}
```

Next, update your account configuration to specify what contact roles can or must be associated with the entity, and their associated types. For example, here is a simple `ConsumerAccount` definition that references the `agent` contact role:

```javascript
{
    "displayName" : "Consumer Account",
    "data" : {
        // ...
    },
    "contacts": {
        "agent?": ["Person"]
    }
}
```

In this case, we use [quantifiers](/configuration/general-topics/quantifiers) to indicate that an association with an `agent` is optional.

The value is an array so that other types of contacts could also be specified as valid types for that role in association with the entity.

After deployment, you can use the [Contacts API](/api/contacts) to create the contact, and then reference the `locator` or `staticLocator` when you create an account that should be associated with the agent. The following is a sample account creation request with a contact reference:

```javascript
{
    "type": "ConsumerAccount",
    "delinquencyPlanName": "Standard",
    "data": {
        "firstName": "Smitham",
        "lastName": "Lowell"
    },
    "contacts": [{
        "contactLocator": "{contactLocator}",
        "roles": ["agent"]
    }]
}
```

Contacts follow the same distinction between instance locators and static locators as elsewhere in the system. When you update a contact, its static locator remains constant, but the updated version obtains a new instance locator. Use static locators for contact associations if you don't need to associate specific contact versions with an entity; else, use instance locators. When you use static locators for contact associations, the static locator points to the latest instance of the contact.

<Callout>
  When <ApiLink name="getContact">fetching a contact</ApiLink>, you need to supply a locator, not a static locator. If you only have a static locator and want more information for a contact, use the static locator with the <ApiLink name="listContacts">list contacts</ApiLink> endpoint, which contains full contact entries for all versions of the contact.
</Callout>

Of course, you can associate your new contact with an existing account. There are contact management endpoints in the [Accounts API](/api/accounts), such as the ability to <ApiLink name="addAccountContact">add an account contact</ApiLink>.

<Callout>
  Validation of the account entity will be blocked if associated agent contacts have not been validated.
</Callout>

<span id="merging-contacts" />

Merging Contacts [#merging-contacts]

The <ApiLink name="mergeContacts" /> endpoint is available to facilitate duplicate contact cleanup. Simply provide the set of static locators for the duplicate contacts in the `contactLocators` array, and a target `mergeToContact` static locator for the set. When executed,

* All the contacts in `contactLocators` will be `discarded`.
* Discarded contact locators will be remapped to the new contact, so that contact lookups by discarded locator will return the new `mergeToContact` target. Contact references using instance locators will point to the latest contact revision with the `mergeToContact` static locator at the time of merging.

Searchability [#searchability]

By default, contacts are not searchable. To enable searches for a contact type, set the `defaultSearchable` property to `true`. Contact search configuration follows the same standards as for other entities; see the [Search Feature Guide](/features/search) for details.


## API Reference

ContactRef
Properties:
  abstract (boolean)
  extend (string)
  defaultSearchable (boolean)
  data (map<string, PropertyRef>, required)